ecom_core 1.2.27 → 1.2.32
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/controllers/concerns/ecom/core/filterable.rb +14 -0
- data/app/controllers/ecom/core/companies_controller.rb +15 -0
- data/app/controllers/ecom/core/project_crews_controller.rb +25 -0
- data/app/controllers/ecom/core/projects_controller.rb +32 -0
- data/app/models/ecom/core/cost_type.rb +8 -0
- data/app/models/ecom/core/crew.rb +13 -1
- data/app/models/ecom/core/crew_time.rb +10 -2
- data/app/models/ecom/core/dimension_element.rb +22 -0
- data/app/models/ecom/core/job_card.rb +16 -0
- data/app/models/ecom/core/maintenance_category.rb +6 -0
- data/app/models/ecom/core/maintenance_cost.rb +10 -0
- data/app/models/ecom/core/maintenance_service_order.rb +19 -0
- data/app/models/ecom/core/maintenance_status.rb +6 -0
- data/app/models/ecom/core/maintenance_type.rb +9 -0
- data/app/models/ecom/core/measurement_unit.rb +55 -0
- data/app/models/ecom/core/overtime_sheet.rb +15 -5
- data/app/models/ecom/core/plan.rb +18 -0
- data/app/models/ecom/core/schedule_setting.rb +11 -0
- data/app/models/ecom/core/schedule_unit.rb +6 -0
- data/app/models/ecom/core/takeoff.rb +10 -0
- data/app/models/ecom/core/takeoff_calculator.rb +115 -0
- data/app/models/ecom/core/task.rb +11 -0
- data/app/models/ecom/core/task_resource.rb +2 -0
- data/app/models/ecom/core/task_step.rb +85 -0
- data/app/models/ecom/core/task_step_dependency.rb +10 -0
- data/app/models/ecom/core/task_template.rb +92 -0
- data/app/models/ecom/core/work_order.rb +26 -0
- data/app/models/ecom/core/work_product.rb +1 -0
- data/app/services/ecom/core/project_crew_service.rb +39 -0
- data/config/routes.rb +5 -0
- data/db/migrate/20191119012027_create_ecom_core_takeoff_calculators.rb +11 -0
- data/db/migrate/20191119012030_create_ecom_core_task_templates.rb +7 -0
- data/db/migrate/20191202235434_create_ecom_core_work_products.rb +0 -1
- data/db/migrate/{20191225100054_create_ecom_core_crews.rb → 20191207103729_create_ecom_core_crews.rb} +3 -3
- data/db/migrate/20191207103730_create_ecom_core_plans.rb +12 -0
- data/db/migrate/20191207103731_create_ecom_core_work_orders.rb +23 -0
- data/db/migrate/20191207103735_create_ecom_core_tasks.rb +9 -1
- data/db/migrate/20200813165553_create_ecom_core_measurement_units.rb +14 -0
- data/db/migrate/20200814043632_create_ecom_core_takeoffs.rb +14 -0
- data/db/migrate/20200820123719_create_ecom_core_task_steps.rb +17 -0
- data/db/migrate/20200821130934_create_ecom_core_task_step_dependencies.rb +16 -0
- data/db/migrate/20200901134912_create_ecom_core_dimension_elements.rb +23 -0
- data/db/migrate/20200919053331_create_ecom_core_maintenance_types.rb +14 -0
- data/db/migrate/20200919072216_create_ecom_core_schedule_settings.rb +21 -0
- data/db/migrate/20200919081338_create_ecom_core_maintenance_service_orders.rb +32 -0
- data/db/migrate/20200919085613_create_ecom_core_job_cards.rb +48 -0
- data/db/migrate/20200919101941_create_ecom_core_cost_types.rb +10 -0
- data/db/migrate/20200919102802_create_ecom_core_maintenance_costs.rb +19 -0
- data/db/migrate/20200922044959_add_costs_approved_to_job_card.rb +5 -0
- data/lib/ecom/core/version.rb +1 -1
- data/spec/factories/dimension_elements.rb +8 -0
- data/spec/factories/ecom/core/attendance_sheet_entries.rb +1 -1
- data/spec/factories/ecom/core/cost_types.rb +6 -0
- data/spec/factories/ecom/core/job_cards.rb +17 -0
- data/spec/factories/ecom/core/maintenance_categories.rb +5 -0
- data/spec/factories/ecom/core/maintenance_costs.rb +9 -0
- data/spec/factories/ecom/core/maintenance_service_orders.rb +16 -0
- data/spec/factories/ecom/core/maintenance_statuses.rb +5 -0
- data/spec/factories/ecom/core/maintenance_types.rb +7 -0
- data/spec/factories/ecom/core/plans.rb +8 -0
- data/spec/factories/ecom/core/schedule_settings.rb +8 -0
- data/spec/factories/ecom/core/schedule_units.rb +5 -0
- data/spec/factories/ecom/core/takeoff_calculators.rb +18 -0
- data/spec/factories/ecom/core/takeoffs.rb +6 -0
- data/spec/factories/ecom/core/task_step_dependencies.rb +6 -0
- data/spec/factories/ecom/core/task_steps.rb +8 -0
- data/spec/factories/ecom/core/task_templates.rb +6 -0
- data/spec/factories/ecom/core/work_orders.rb +10 -0
- data/spec/factories/ecom/core/work_products.rb +0 -1
- data/spec/factories/measurement_units.rb +10 -0
- metadata +72 -4
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 18c07bbf068fb4b629257c21df23a45979e0d1f505e4002d0477d3a37926549d
|
|
4
|
+
data.tar.gz: 2c4efc8c1e021bbf12a87805a78722d3d1e093e8a3e53f9a75f7246c665a888d
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 11bbca4344928bcd49f1256c6566b135467a943458be8744e78d11af0dd1626187a68a93655ee3d875a9938a4f5e87000b8c58fb4a216d0a6da5ff918997059e
|
|
7
|
+
data.tar.gz: 587ff863a59b121e6184f2db3226b1159c3fbafb536a49d08ec82937bf858a9f307eff4ff4b7eaeb340c850100fd22c4e82e616ec667eaef9b48068abb862f9a
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
module Filterable
|
|
4
|
+
extend ActiveSupport::Concern
|
|
5
|
+
|
|
6
|
+
module ClassMethods
|
|
7
|
+
def filter(filtering_params)
|
|
8
|
+
results = where(nil)
|
|
9
|
+
results.public_send('filter_by_condition', filtering_params) if filtering_params.present?
|
|
10
|
+
end
|
|
11
|
+
end
|
|
12
|
+
end
|
|
13
|
+
end
|
|
14
|
+
end
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
class CompaniesController < ApplicationController
|
|
4
|
+
def index
|
|
5
|
+
data = Ecom::Core::Company.all
|
|
6
|
+
render json: data
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
def default_company
|
|
10
|
+
data = Ecom::Core::Company.first
|
|
11
|
+
render json: data
|
|
12
|
+
end
|
|
13
|
+
end
|
|
14
|
+
end
|
|
15
|
+
end
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
class ProjectCrewsController < ApplicationController
|
|
4
|
+
before_action :set_service, only: %i[update]
|
|
5
|
+
|
|
6
|
+
def index
|
|
7
|
+
project = Ecom::Core::Project.find(params[:id])
|
|
8
|
+
serialized = ActiveModelSerializers::SerializableResource.new(project.crews)
|
|
9
|
+
render json: { success: true, data: serialized }
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def update
|
|
13
|
+
data = @service.update(params)
|
|
14
|
+
serialized = ActiveModelSerializers::SerializableResource.new(data[:data])
|
|
15
|
+
render json: { success: true, data: serialized }
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
private
|
|
19
|
+
|
|
20
|
+
def set_service
|
|
21
|
+
@service = ProjectCrewService.new
|
|
22
|
+
end
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
end
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
class ProjectsController < ApplicationController
|
|
4
|
+
before_action :set_project, only: %i[show]
|
|
5
|
+
# GET /projects
|
|
6
|
+
def index
|
|
7
|
+
projects = Ecom::Core::Project.includes(:employer, :contractor, :consultant, :project_manager)
|
|
8
|
+
.where(company_id: params[:id])
|
|
9
|
+
serialized = ActiveModelSerializers::SerializableResource.new(projects)
|
|
10
|
+
render json: { success: true, data: serialized }
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
def show
|
|
14
|
+
render json: @project
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
private
|
|
18
|
+
|
|
19
|
+
def set_project
|
|
20
|
+
@project = Project.find(params[:id])
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def model_params
|
|
24
|
+
params.require(:project).permit(:name, :description, :location, :objective, :project_scope, :employer_id,
|
|
25
|
+
:contractor_id, :consultant_id, :project_manager_id, :contract_number,
|
|
26
|
+
:company_id, :date_contract_signed, :commencement_date, :completion_date,
|
|
27
|
+
:contract_amount, :advance_payment, :retention, :remark, :task_template_type_id,
|
|
28
|
+
:currency_id)
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
end
|
|
@@ -10,11 +10,16 @@ module Ecom
|
|
|
10
10
|
before_save :set_employment_date,
|
|
11
11
|
if: proc { |c| c.employment_date.nil? }
|
|
12
12
|
|
|
13
|
+
after_save :set_employee_id
|
|
14
|
+
|
|
13
15
|
belongs_to :crew_type
|
|
14
16
|
|
|
15
|
-
validates :name, :address, :qualification, :employment, :wage, :
|
|
17
|
+
validates :name, :address, :qualification, :employment, :wage, :guarantor_name, :guarantor_phone, presence: true
|
|
16
18
|
validates :employment, inclusion: EMPLOYMENT_TYPES
|
|
17
19
|
|
|
20
|
+
has_many :project_crews
|
|
21
|
+
has_many :projects, through: :project_crews
|
|
22
|
+
|
|
18
23
|
scope :by_active, ->(active) { where(active: active) }
|
|
19
24
|
scope :by_qualification, ->(qualification) { where(qualification: qualification) }
|
|
20
25
|
scope :by_sub_contracted, ->(sub_contracted) { where(sub_contracted: sub_contracted) }
|
|
@@ -22,6 +27,13 @@ module Ecom
|
|
|
22
27
|
def set_employment_date
|
|
23
28
|
self.employment_date = Date.today
|
|
24
29
|
end
|
|
30
|
+
|
|
31
|
+
def set_employee_id
|
|
32
|
+
company = Ecom::Core::Company.first
|
|
33
|
+
date = employment_date.to_s[0..3]
|
|
34
|
+
company_name = company ? company.name : ''
|
|
35
|
+
self.employee_id = "#{company_name}/#{employment}/#{date}/#{id}"
|
|
36
|
+
end
|
|
25
37
|
end
|
|
26
38
|
end
|
|
27
39
|
end
|
|
@@ -12,7 +12,7 @@ module Ecom
|
|
|
12
12
|
has_one :revision, class_name: 'Ecom::Core::CrewTime', foreign_key: :revision_to_id
|
|
13
13
|
|
|
14
14
|
validates :checkin_time, presence: true, if: :checkout_time
|
|
15
|
-
validate :
|
|
15
|
+
validate :time_range_validation, :total_time_validation
|
|
16
16
|
|
|
17
17
|
scope :by_attendance, lambda { |id|
|
|
18
18
|
joins(:attendance_sheet_entry).where(ecom_core_attendance_sheet_entries: { attendance_sheet_id: id })
|
|
@@ -22,12 +22,20 @@ module Ecom
|
|
|
22
22
|
before_save :calculate_hours
|
|
23
23
|
after_save :calculate_total
|
|
24
24
|
|
|
25
|
-
def
|
|
25
|
+
def time_range_validation
|
|
26
26
|
return unless checkin_time && checkout_time && checkout_time <= checkin_time
|
|
27
27
|
|
|
28
28
|
errors.add(:checkout_time, "can't be less than checkin time.")
|
|
29
29
|
end
|
|
30
30
|
|
|
31
|
+
def total_time_validation
|
|
32
|
+
return if checkout_time.nil? || checkin_time.nil?
|
|
33
|
+
|
|
34
|
+
return unless attendance_sheet_entry.total_hours + compute_hours > 8
|
|
35
|
+
|
|
36
|
+
errors.add(:attendance_sheet_entry, 'has more than 8 hours')
|
|
37
|
+
end
|
|
38
|
+
|
|
31
39
|
def calculate_hours
|
|
32
40
|
self.hours = if checkout_time.nil? || checkin_time.nil?
|
|
33
41
|
0
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
class DimensionElement < ApplicationRecord
|
|
4
|
+
LENGTH = 'Length'.freeze
|
|
5
|
+
WIDTH = 'Width'.freeze
|
|
6
|
+
HEIGHT = 'Height'.freeze
|
|
7
|
+
RADIUS = 'Radius'.freeze
|
|
8
|
+
DIAMETER = 'Diameter'.freeze
|
|
9
|
+
DIMENSION_ELEMENT_NAMES = %w[LENGTH WIDTH HEIGHT RADIUS DIAMETER].freeze
|
|
10
|
+
|
|
11
|
+
validates :work_product_id, :work_product, :measurement_unit_id, :measurement_unit,
|
|
12
|
+
:amount, :dimension_element_name, presence: true
|
|
13
|
+
|
|
14
|
+
validates :dimension_element_name, inclusion: DIMENSION_ELEMENT_NAMES
|
|
15
|
+
|
|
16
|
+
validates :amount, numericality: { greater_than: 0 }
|
|
17
|
+
|
|
18
|
+
belongs_to :work_product
|
|
19
|
+
belongs_to :measurement_unit
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
end
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
class JobCard < ApplicationRecord
|
|
4
|
+
belongs_to :maintenance_service_order
|
|
5
|
+
belongs_to :service_provider, class_name: 'Ecom::Core::EquipmentLocation'
|
|
6
|
+
belongs_to :checkout_by, class_name: 'Ecom::Core::User', optional: true
|
|
7
|
+
belongs_to :checkout_to, class_name: 'Ecom::Core::EquipmentLocation', optional: true
|
|
8
|
+
belongs_to :maintenance_status
|
|
9
|
+
belongs_to :checkin_by, class_name: 'Ecom::Core::User', optional: true
|
|
10
|
+
belongs_to :checkin_to, class_name: 'Ecom::Core::EquipmentLocation', optional: true
|
|
11
|
+
belongs_to :prepared_by, class_name: 'Ecom::Core::User'
|
|
12
|
+
|
|
13
|
+
validates :code, presence: true, uniqueness: true
|
|
14
|
+
end
|
|
15
|
+
end
|
|
16
|
+
end
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
class MaintenanceServiceOrder < ApplicationRecord
|
|
4
|
+
NEW = 'New'.freeze
|
|
5
|
+
IN_PROGRESS = 'In Progress'.freeze
|
|
6
|
+
COMPLETED = 'Completed'.freeze
|
|
7
|
+
|
|
8
|
+
STATUSES = [NEW, IN_PROGRESS, COMPLETED].freeze
|
|
9
|
+
|
|
10
|
+
belongs_to :equipment_item
|
|
11
|
+
belongs_to :maintenance_type
|
|
12
|
+
belongs_to :prepared_by, class_name: 'Ecom::Core::User'
|
|
13
|
+
belongs_to :approved_by, class_name: 'Ecom::Core::User'
|
|
14
|
+
|
|
15
|
+
validates :title, :status, :current_reading, presence: true
|
|
16
|
+
validates :status, inclusion: STATUSES
|
|
17
|
+
end
|
|
18
|
+
end
|
|
19
|
+
end
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
class MeasurementUnit < ApplicationRecord
|
|
4
|
+
METRIC = 'Metric'.freeze
|
|
5
|
+
IMPERIAL = 'Imperial'.freeze
|
|
6
|
+
SYSTEM_OF_MEASURMENT = [METRIC, IMPERIAL].freeze
|
|
7
|
+
|
|
8
|
+
# commonly used physical quantities in construction
|
|
9
|
+
LENGTH = 'Length'.freeze
|
|
10
|
+
MASS = 'Mass'.freeze
|
|
11
|
+
TIME = 'Time'.freeze
|
|
12
|
+
CURRENT = 'Current'.freeze
|
|
13
|
+
TEMPRATURE = 'Temprature'.freeze
|
|
14
|
+
|
|
15
|
+
AREA = 'Area'.freeze
|
|
16
|
+
VOLUME = 'Volume'.freeze
|
|
17
|
+
ENERGY = 'Energy'.freeze
|
|
18
|
+
DENSITY = 'DENSITY'.freeze
|
|
19
|
+
|
|
20
|
+
PHYSICAL_QUANTITIES = [LENGTH, MASS, TIME, CURRENT, TEMPRATURE, AREA, VOLUME, ENERGY, DENSITY].freeze
|
|
21
|
+
|
|
22
|
+
validates :name, :abbrivation, :physical_quantity,
|
|
23
|
+
:conversion_factor, :system_of_measurement, presence: true
|
|
24
|
+
|
|
25
|
+
validates :is_si_unit, inclusion: { in: [true, false] }
|
|
26
|
+
|
|
27
|
+
validates :system_of_measurement, inclusion: SYSTEM_OF_MEASURMENT
|
|
28
|
+
validates :physical_quantity, inclusion: PHYSICAL_QUANTITIES
|
|
29
|
+
|
|
30
|
+
validate :si_unit_with_conversion_factor
|
|
31
|
+
validate :si_unit_system_of_measurement_and_physical_quantity
|
|
32
|
+
|
|
33
|
+
def si_unit_with_conversion_factor
|
|
34
|
+
if is_si_unit && conversion_factor != 1
|
|
35
|
+
errors.add(:base, 'Conversion factor for an SI unit has to be 1')
|
|
36
|
+
elsif !is_si_unit && conversion_factor == 1
|
|
37
|
+
errors.add(:base, 'Only SI units can have a conversion factor 1')
|
|
38
|
+
end
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
# scope si unit with system of measurement and physical quantity
|
|
42
|
+
def si_unit_system_of_measurement_and_physical_quantity
|
|
43
|
+
return if system_of_measurement.nil? || physical_quantity.nil?
|
|
44
|
+
|
|
45
|
+
existing_record = MeasurementUnit
|
|
46
|
+
.where(system_of_measurement: system_of_measurement,
|
|
47
|
+
physical_quantity: physical_quantity, is_si_unit: true).first
|
|
48
|
+
return unless (new_record? && existing_record.present?) || (persisted? && existing_record != self)
|
|
49
|
+
|
|
50
|
+
errors.add(:is_si_unit,
|
|
51
|
+
'There exist an si unit of measurement for the given physical quantity and system of measurement')
|
|
52
|
+
end
|
|
53
|
+
end
|
|
54
|
+
end
|
|
55
|
+
end
|
|
@@ -13,19 +13,29 @@ module Ecom
|
|
|
13
13
|
scope :by_date, ->(date) { where(date: date) }
|
|
14
14
|
scope :by_status, ->(status) { where(status: status) }
|
|
15
15
|
scope :by_date_between, ->(from, to) { where('date BETWEEN ? AND ?', from, to) }
|
|
16
|
-
scope :open, ->(id) { where(status: StatusConstants::OPEN, project_id: id) }
|
|
17
|
-
scope :submitted, ->(id) { where(status: StatusConstants::SUBMITTED, project_id: id) }
|
|
16
|
+
# scope :open, ->(id) { where(status: StatusConstants::OPEN, project_id: id) }
|
|
17
|
+
# scope :submitted, ->(id) { where(status: StatusConstants::SUBMITTED, project_id: id) }
|
|
18
18
|
|
|
19
19
|
def self.open_exists?(project_id)
|
|
20
|
-
OvertimeSheet
|
|
20
|
+
OvertimeSheet
|
|
21
|
+
.by_project(project_id)
|
|
22
|
+
.by_status(StatusConstants::OPEN)
|
|
23
|
+
.exists?
|
|
21
24
|
end
|
|
22
25
|
|
|
23
26
|
def self.open_for_date_exists?(date, project_id)
|
|
24
|
-
OvertimeSheet
|
|
27
|
+
OvertimeSheet
|
|
28
|
+
.by_project(project_id)
|
|
29
|
+
.by_status(StatusConstants::OPEN)
|
|
30
|
+
.by_date(date)
|
|
31
|
+
.exists?
|
|
25
32
|
end
|
|
26
33
|
|
|
27
34
|
def self.exists_for_date?(date, project_id)
|
|
28
|
-
OvertimeSheet
|
|
35
|
+
OvertimeSheet
|
|
36
|
+
.by_project(project_id)
|
|
37
|
+
.by_date(date)
|
|
38
|
+
.exists?
|
|
29
39
|
end
|
|
30
40
|
|
|
31
41
|
# Overtime sheet should be created using the
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
class Plan < ApplicationRecord
|
|
4
|
+
NEW = 'New'.freeze
|
|
5
|
+
READY_TO_START = 'Ready to start'.freeze
|
|
6
|
+
IN_PROGRESS = 'In Progress'.freeze
|
|
7
|
+
COMPLETED = 'Completed'.freeze
|
|
8
|
+
|
|
9
|
+
STATUSES = [NEW, READY_TO_START, IN_PROGRESS, COMPLETED].freeze
|
|
10
|
+
|
|
11
|
+
validates :name, :start_date, :end_date, :status, presence: true
|
|
12
|
+
|
|
13
|
+
validates :status, presence: true, inclusion: STATUSES
|
|
14
|
+
|
|
15
|
+
has_many :tasks
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
end
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
module Ecom
|
|
2
|
+
module Core
|
|
3
|
+
class TakeoffCalculator < ApplicationRecord
|
|
4
|
+
INPUT_PARAMETERS_SCHEMA = {
|
|
5
|
+
'type' => 'object',
|
|
6
|
+
'required' => %w[name label input_type],
|
|
7
|
+
'additionalProperties' => false,
|
|
8
|
+
'properties' => {
|
|
9
|
+
'name' => { 'type' => 'string' },
|
|
10
|
+
'label' => { 'type' => 'string' },
|
|
11
|
+
'input_type' => {
|
|
12
|
+
'type' => 'string',
|
|
13
|
+
'enum' => %w[string number measurement enum]
|
|
14
|
+
}
|
|
15
|
+
},
|
|
16
|
+
"patternProperties": {
|
|
17
|
+
"enum_values": {
|
|
18
|
+
'type' => 'array'
|
|
19
|
+
},
|
|
20
|
+
"default_value": {
|
|
21
|
+
'type' => 'object',
|
|
22
|
+
'required' => %w[value],
|
|
23
|
+
'properties' => {
|
|
24
|
+
'value' => { 'type' => 'string' }
|
|
25
|
+
},
|
|
26
|
+
"patternProperties": {
|
|
27
|
+
"measurement_unit_id": { 'type' => 'integer' }
|
|
28
|
+
}
|
|
29
|
+
},
|
|
30
|
+
"validation": {
|
|
31
|
+
'type' => 'object',
|
|
32
|
+
'required' => %w[required],
|
|
33
|
+
'properties' => {
|
|
34
|
+
'required' => { 'type' => 'boolean' }
|
|
35
|
+
},
|
|
36
|
+
"patternProperties": {
|
|
37
|
+
"minimum": { 'type' => 'number' },
|
|
38
|
+
"maximum": { 'type' => 'number' }
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
}.freeze
|
|
43
|
+
|
|
44
|
+
REBAR_TAKEOFF_CALCULATOR = 'Rebar Takeoff Calculator'.freeze
|
|
45
|
+
FORMWORK_TAKEOFF_CALCULATOR = 'Formwork Takeoff Calculator'.freeze
|
|
46
|
+
CONCRETE_POURING_TAKEOFF_CALCULATOR =
|
|
47
|
+
'Concrete Pouring Takeoff Calculator'.freeze
|
|
48
|
+
|
|
49
|
+
TAKEOFF_CALCULATOR_NAMES =
|
|
50
|
+
[
|
|
51
|
+
REBAR_TAKEOFF_CALCULATOR,
|
|
52
|
+
FORMWORK_TAKEOFF_CALCULATOR,
|
|
53
|
+
CONCRETE_POURING_TAKEOFF_CALCULATOR
|
|
54
|
+
].freeze
|
|
55
|
+
|
|
56
|
+
validates :name, :input_parameters, presence: true
|
|
57
|
+
validates :name, inclusion: TAKEOFF_CALCULATOR_NAMES
|
|
58
|
+
|
|
59
|
+
validates :name, uniqueness: true
|
|
60
|
+
|
|
61
|
+
validate :input_parameters_schema
|
|
62
|
+
validate :measurement_unit_id_in_input_parameters
|
|
63
|
+
validate :enum_in_input_parameters
|
|
64
|
+
|
|
65
|
+
def input_parameters_schema
|
|
66
|
+
return if input_parameters.nil?
|
|
67
|
+
|
|
68
|
+
errors.add(:input_parameters, 'There has to be one or more input parameters') if input_parameters.count.zero?
|
|
69
|
+
|
|
70
|
+
validation_errors = JSON::Validator.fully_validate(INPUT_PARAMETERS_SCHEMA,
|
|
71
|
+
input_parameters, strict: true,
|
|
72
|
+
list: true, clear_cache: true)
|
|
73
|
+
|
|
74
|
+
errors.add(:input_parameters, validation_errors) unless validation_errors.empty?
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
def measurement_unit_id_in_input_parameters
|
|
78
|
+
return if input_parameters.nil?
|
|
79
|
+
|
|
80
|
+
input_parameters.each do |input_parameter|
|
|
81
|
+
next unless input_parameter['input_type'] == 'measurement' && !input_parameter['default_value'].nil?
|
|
82
|
+
|
|
83
|
+
if input_parameter['default_value']['measurement_unit_id'].nil?
|
|
84
|
+
errors.add(:base, 'measurement_unit_id is required')
|
|
85
|
+
next
|
|
86
|
+
end
|
|
87
|
+
|
|
88
|
+
measurement_unit_id = input_parameter['default_value']['measurement_unit_id']
|
|
89
|
+
measurement_unit = Ecom::Core::MeasurementUnit.find_by(id: measurement_unit_id)
|
|
90
|
+
|
|
91
|
+
errors.add(:base, "measurement unit with id #{measurement_unit_id} does not exist") if measurement_unit.nil?
|
|
92
|
+
end
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
def enum_in_input_parameters
|
|
96
|
+
return if input_parameters.nil?
|
|
97
|
+
|
|
98
|
+
input_parameters.each do |input_parameter|
|
|
99
|
+
next if input_parameter['input_type'] != 'enum'
|
|
100
|
+
|
|
101
|
+
if input_parameter['enum_values'].nil?
|
|
102
|
+
errors.add(:base, 'enum_values are requiered if the input_type is enum')
|
|
103
|
+
next
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
next unless !input_parameter['enum_values'].nil? &&
|
|
107
|
+
input_parameter['enum_values'].class == Array &&
|
|
108
|
+
input_parameter['enum_values'].count.zero?
|
|
109
|
+
|
|
110
|
+
errors.add(:base, 'Provide at least one enum value')
|
|
111
|
+
end
|
|
112
|
+
end
|
|
113
|
+
end
|
|
114
|
+
end
|
|
115
|
+
end
|