dscf-credit 0.1.0
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 +7 -0
- data/MIT-LICENSE +20 -0
- data/README.md +28 -0
- data/Rakefile +8 -0
- data/app/controllers/dscf/credit/application_controller.rb +8 -0
- data/app/controllers/dscf/credit/bank_branches_controller.rb +38 -0
- data/app/controllers/dscf/credit/bank_staffs_controller.rb +77 -0
- data/app/controllers/dscf/credit/banks_controller.rb +39 -0
- data/app/controllers/dscf/credit/categories_controller.rb +32 -0
- data/app/controllers/dscf/credit/credit_line_specs_controller.rb +72 -0
- data/app/controllers/dscf/credit/credit_lines_controller.rb +76 -0
- data/app/controllers/dscf/credit/facilitators_controller.rb +227 -0
- data/app/controllers/dscf/credit/loans_controller.rb +41 -0
- data/app/controllers/dscf/credit/parameter_normalizers_controller.rb +31 -0
- data/app/controllers/dscf/credit/payment_requests_controller.rb +38 -0
- data/app/controllers/dscf/credit/payments_controller.rb +36 -0
- data/app/controllers/dscf/credit/scoring_parameters_controller.rb +50 -0
- data/app/controllers/dscf/credit/scoring_tables_controller.rb +63 -0
- data/app/controllers/dscf/credit/system_config_definitions_controller.rb +34 -0
- data/app/controllers/dscf/credit/system_configs_controller.rb +49 -0
- data/app/controllers/dscf/credit/users_controller.rb +53 -0
- data/app/jobs/dscf/credit/application_job.rb +6 -0
- data/app/mailers/dscf/credit/application_mailer.rb +8 -0
- data/app/mailers/dscf/credit/bank_staff_welcome_mailer.rb +15 -0
- data/app/mailers/dscf/credit/facilitator_mailer.rb +54 -0
- data/app/models/dscf/credit/accounting_audit_request.rb +17 -0
- data/app/models/dscf/credit/accounting_entry.rb +15 -0
- data/app/models/dscf/credit/application_record.rb +7 -0
- data/app/models/dscf/credit/bank.rb +38 -0
- data/app/models/dscf/credit/bank_branch.rb +23 -0
- data/app/models/dscf/credit/bank_staff.rb +26 -0
- data/app/models/dscf/credit/category.rb +21 -0
- data/app/models/dscf/credit/credit_line.rb +30 -0
- data/app/models/dscf/credit/credit_line_spec.rb +37 -0
- data/app/models/dscf/credit/daily_routine_transaction.rb +18 -0
- data/app/models/dscf/credit/facilitator.rb +31 -0
- data/app/models/dscf/credit/facilitator_performance.rb +17 -0
- data/app/models/dscf/credit/failed_operations_log.rb +17 -0
- data/app/models/dscf/credit/loan.rb +33 -0
- data/app/models/dscf/credit/loan_profile.rb +43 -0
- data/app/models/dscf/credit/loan_profile_scoring_spec.rb +23 -0
- data/app/models/dscf/credit/loan_transaction.rb +17 -0
- data/app/models/dscf/credit/parameter_normalizer.rb +11 -0
- data/app/models/dscf/credit/payment.rb +22 -0
- data/app/models/dscf/credit/payment_request.rb +29 -0
- data/app/models/dscf/credit/scoring_parameter.rb +30 -0
- data/app/models/dscf/credit/scoring_table.rb +24 -0
- data/app/models/dscf/credit/system_config.rb +25 -0
- data/app/models/dscf/credit/system_config_definition.rb +25 -0
- data/app/serializers/dscf/core/business_serializer.rb +9 -0
- data/app/serializers/dscf/core/business_type_serializer.rb +7 -0
- data/app/serializers/dscf/core/role_serializer.rb +7 -0
- data/app/serializers/dscf/core/user_profile_serializer.rb +13 -0
- data/app/serializers/dscf/core/user_role_serializer.rb +16 -0
- data/app/serializers/dscf/core/user_serializer.rb +17 -0
- data/app/serializers/dscf/credit/bank_branch_serializer.rb +9 -0
- data/app/serializers/dscf/credit/bank_serializer.rb +9 -0
- data/app/serializers/dscf/credit/bank_staff_serializer.rb +8 -0
- data/app/serializers/dscf/credit/category_serializer.rb +7 -0
- data/app/serializers/dscf/credit/credit_line_serializer.rb +12 -0
- data/app/serializers/dscf/credit/credit_line_spec_serializer.rb +12 -0
- data/app/serializers/dscf/credit/parameter_normalizer_serializer.rb +8 -0
- data/app/serializers/dscf/credit/scoring_parameter_serializer.rb +12 -0
- data/app/serializers/dscf/credit/scoring_table_serializer.rb +9 -0
- data/app/serializers/dscf/credit/system_config_definition_serializer.rb +9 -0
- data/app/serializers/dscf/credit/system_config_serializer.rb +18 -0
- data/app/services/dscf/credit/bank_staff_creation_service.rb +99 -0
- data/app/services/dscf/credit/facilitator_additional_info_service.rb +62 -0
- data/app/services/dscf/credit/facilitator_approval_service.rb +88 -0
- data/app/views/dscf/credit/bank_staff_welcome_mailer/welcome_email.html.erb +116 -0
- data/app/views/dscf/credit/bank_staff_welcome_mailer/welcome_email.text.erb +40 -0
- data/app/views/dscf/credit/facilitator_mailer/additional_info_received.html.erb +39 -0
- data/app/views/dscf/credit/facilitator_mailer/additional_info_received.text.erb +17 -0
- data/app/views/dscf/credit/facilitator_mailer/approval_notification.html.erb +59 -0
- data/app/views/dscf/credit/facilitator_mailer/approval_notification.text.erb +26 -0
- data/app/views/dscf/credit/facilitator_mailer/limit_update_notification.html.erb +39 -0
- data/app/views/dscf/credit/facilitator_mailer/limit_update_notification.text.erb +17 -0
- data/app/views/dscf/credit/facilitator_mailer/rejection_notification.html.erb +41 -0
- data/app/views/dscf/credit/facilitator_mailer/rejection_notification.text.erb +19 -0
- data/app/views/layouts/mailer.html.erb +125 -0
- data/app/views/layouts/mailer.text.erb +12 -0
- data/config/locales/en.yml +208 -0
- data/config/routes.rb +50 -0
- data/db/migrate/20250822091011_create_dscf_credit_categories.rb +15 -0
- data/db/migrate/20250822091015_create_dscf_credit_banks.rb +23 -0
- data/db/migrate/20250822091055_create_dscf_credit_bank_branches.rb +23 -0
- data/db/migrate/20250822091131_create_dscf_credit_credit_lines.rb +25 -0
- data/db/migrate/20250822091527_create_dscf_credit_credit_line_specs.rb +32 -0
- data/db/migrate/20250822091744_create_dscf_credit_system_config_definitions.rb +18 -0
- data/db/migrate/20250822091820_create_dscf_credit_system_configs.rb +17 -0
- data/db/migrate/20250822092050_create_dscf_credit_scoring_parameters.rb +30 -0
- data/db/migrate/20250822092225_create_dscf_credit_parameter_normalizers.rb +18 -0
- data/db/migrate/20250822092246_create_dscf_credit_loan_profiles.rb +25 -0
- data/db/migrate/20250822092417_create_dscf_credit_loan_profile_scoring_specs.rb +23 -0
- data/db/migrate/20250822092436_create_dscf_credit_facilitators.rb +22 -0
- data/db/migrate/20250822092528_create_dscf_credit_facilitator_performances.rb +26 -0
- data/db/migrate/20250822092608_create_dscf_credit_payment_requests.rb +26 -0
- data/db/migrate/20250822092654_create_dscf_credit_loans.rb +29 -0
- data/db/migrate/20250822092717_create_dscf_credit_loan_transactions.rb +21 -0
- data/db/migrate/20250822092738_create_dscf_credit_daily_routine_transactions.rb +23 -0
- data/db/migrate/20250822092819_create_dscf_credit_accounting_audit_requests.rb +20 -0
- data/db/migrate/20250822092843_create_dscf_credit_payments.rb +23 -0
- data/db/migrate/20250822092908_create_dscf_credit_failed_operations_logs.rb +21 -0
- data/db/migrate/20250822092936_create_dscf_credit_accounting_entries.rb +21 -0
- data/db/migrate/20250825231109_create_dscf_credit_bank_staff.rb +14 -0
- data/db/migrate/20250901172842_create_dscf_credit_scoring_tables.rb +18 -0
- data/db/seeds.rb +745 -0
- data/lib/dscf/credit/engine.rb +28 -0
- data/lib/dscf/credit/version.rb +5 -0
- data/lib/dscf/credit.rb +9 -0
- data/lib/tasks/dscf/credit_tasks.rake +4 -0
- data/spec/factories/dscf/credit/accounting_audit_requests.rb +58 -0
- data/spec/factories/dscf/credit/accounting_entries.rb +29 -0
- data/spec/factories/dscf/credit/bank_branches.rb +21 -0
- data/spec/factories/dscf/credit/bank_staffs.rb +19 -0
- data/spec/factories/dscf/credit/banks.rb +30 -0
- data/spec/factories/dscf/credit/categories.rb +27 -0
- data/spec/factories/dscf/credit/credit_line_specs.rb +57 -0
- data/spec/factories/dscf/credit/credit_lines.rb +32 -0
- data/spec/factories/dscf/credit/daily_routine_transactions.rb +36 -0
- data/spec/factories/dscf/credit/facilitator_performances.rb +30 -0
- data/spec/factories/dscf/credit/facilitators.rb +35 -0
- data/spec/factories/dscf/credit/failed_operations_logs.rb +34 -0
- data/spec/factories/dscf/credit/loan_profile_scoring_specs.rb +31 -0
- data/spec/factories/dscf/credit/loan_profiles.rb +49 -0
- data/spec/factories/dscf/credit/loan_transactions.rb +37 -0
- data/spec/factories/dscf/credit/loans.rb +37 -0
- data/spec/factories/dscf/credit/parameter_normalizers.rb +24 -0
- data/spec/factories/dscf/credit/payment_requests.rb +40 -0
- data/spec/factories/dscf/credit/payments.rb +39 -0
- data/spec/factories/dscf/credit/scoring_parameters.rb +48 -0
- data/spec/factories/dscf/credit/scoring_tables.rb +25 -0
- data/spec/factories/dscf/credit/system_config_definitions.rb +45 -0
- data/spec/factories/dscf/credit/system_configs.rb +29 -0
- metadata +456 -0
data/db/seeds.rb
ADDED
@@ -0,0 +1,745 @@
|
|
1
|
+
# DSCF Credit Engine Seed Data
|
2
|
+
# This file seeds the database with sample data for all models in the correct dependency order
|
3
|
+
|
4
|
+
puts "Starting DSCF Credit Engine seed data..."
|
5
|
+
|
6
|
+
# First, seed business types from dscf-core
|
7
|
+
puts "Seeding business types..."
|
8
|
+
if defined?(Dscf::Core::BusinessType)
|
9
|
+
individual_business_type = Dscf::Core::BusinessType.find_or_create_by(name: 'individual')
|
10
|
+
corporate_business_type = Dscf::Core::BusinessType.find_or_create_by(name: 'corporate')
|
11
|
+
agent_business_type = Dscf::Core::BusinessType.find_or_create_by(name: 'agent')
|
12
|
+
puts "✓ Business types created/found"
|
13
|
+
end
|
14
|
+
|
15
|
+
# Create roles for the system if needed
|
16
|
+
puts "Seeding roles..."
|
17
|
+
if defined?(Dscf::Core::Role)
|
18
|
+
admin_role = Dscf::Core::Role.find_or_create_by(code: 'admin') do |role|
|
19
|
+
role.name = 'System Administrator'
|
20
|
+
end
|
21
|
+
|
22
|
+
bank_admin_role = Dscf::Core::Role.find_or_create_by(code: 'bank_admin') do |role|
|
23
|
+
role.name = 'Bank Administrator'
|
24
|
+
end
|
25
|
+
|
26
|
+
bank_staff_role = Dscf::Core::Role.find_or_create_by(code: 'bank_staff') do |role|
|
27
|
+
role.name = 'Bank Staff'
|
28
|
+
end
|
29
|
+
|
30
|
+
facilitator_role = Dscf::Core::Role.find_or_create_by(code: 'facilitator') do |role|
|
31
|
+
role.name = 'Facilitator'
|
32
|
+
end
|
33
|
+
|
34
|
+
puts "✓ Roles created/found"
|
35
|
+
end
|
36
|
+
|
37
|
+
# Create users and their businesses from dscf-core if needed
|
38
|
+
# This would typically be seeded by the core engine, but we'll reference existing users
|
39
|
+
puts "Checking for existing users..."
|
40
|
+
|
41
|
+
# users is from dscf-core engine
|
42
|
+
if defined?(Dscf::Core::User)
|
43
|
+
admin_user = Dscf::Core::User.find_or_create_by(email: 'admin@bunna.com') do |user|
|
44
|
+
user.phone = '+251911123456'
|
45
|
+
user.verified_at = Time.current
|
46
|
+
user.temp_password = false
|
47
|
+
user.password = 'SecurePassword123!'
|
48
|
+
end
|
49
|
+
|
50
|
+
bank_admin = Dscf::Core::User.find_or_create_by(email: 'bank.admin@bunna.com') do |user|
|
51
|
+
user.phone = '+251922123456'
|
52
|
+
user.verified_at = Time.current
|
53
|
+
user.temp_password = false
|
54
|
+
user.password = 'SecurePassword123!'
|
55
|
+
end
|
56
|
+
|
57
|
+
user1 = Dscf::Core::User.find_or_create_by(email: 'user1@bunna.com') do |user|
|
58
|
+
user.phone = '+251933123456'
|
59
|
+
user.verified_at = Time.current
|
60
|
+
user.temp_password = false
|
61
|
+
user.password = 'SecurePassword123!'
|
62
|
+
end
|
63
|
+
|
64
|
+
user2 = Dscf::Core::User.find_or_create_by(email: 'user2@bunna.com') do |user|
|
65
|
+
user.phone = '+251944123456'
|
66
|
+
user.verified_at = Time.current
|
67
|
+
user.temp_password = false
|
68
|
+
user.password = 'SecurePassword123!'
|
69
|
+
end
|
70
|
+
|
71
|
+
# Create additional test users for batch testing
|
72
|
+
user3 = Dscf::Core::User.find_or_create_by(email: 'user3@bunna.com') do |user|
|
73
|
+
user.phone = '+251955123456'
|
74
|
+
user.verified_at = Time.current
|
75
|
+
user.temp_password = false
|
76
|
+
user.password = 'SecurePassword123!'
|
77
|
+
end
|
78
|
+
|
79
|
+
user4 = Dscf::Core::User.find_or_create_by(email: 'user4@bunna.com') do |user|
|
80
|
+
user.phone = '+251966123456'
|
81
|
+
user.verified_at = Time.current
|
82
|
+
user.temp_password = false
|
83
|
+
user.password = 'SecurePassword123!'
|
84
|
+
end
|
85
|
+
|
86
|
+
puts "✓ Users created/found"
|
87
|
+
|
88
|
+
# Create businesses for users
|
89
|
+
puts "Seeding businesses..."
|
90
|
+
if defined?(Dscf::Core::Business) && defined?(Dscf::Core::BusinessType)
|
91
|
+
# Create business for user1 (Individual)
|
92
|
+
business1 = Dscf::Core::Business.find_or_create_by(
|
93
|
+
user_id: user1.id,
|
94
|
+
business_type_id: individual_business_type.id
|
95
|
+
) do |business|
|
96
|
+
business.name = 'Individual Trading Business'
|
97
|
+
business.description = 'Individual business for trading services'
|
98
|
+
business.contact_email = user1.email
|
99
|
+
business.contact_phone = user1.phone
|
100
|
+
end
|
101
|
+
|
102
|
+
# Create business for user2 (Corporate)
|
103
|
+
business2 = Dscf::Core::Business.find_or_create_by(
|
104
|
+
user_id: user2.id,
|
105
|
+
business_type_id: corporate_business_type.id
|
106
|
+
) do |business|
|
107
|
+
business.name = 'Manufacturing Corp'
|
108
|
+
business.description = 'Corporate manufacturing business'
|
109
|
+
business.contact_email = user2.email
|
110
|
+
business.contact_phone = user2.phone
|
111
|
+
end
|
112
|
+
|
113
|
+
# Create business for user3 (Corporate)
|
114
|
+
business3 = Dscf::Core::Business.find_or_create_by(
|
115
|
+
user_id: user3.id,
|
116
|
+
business_type_id: corporate_business_type.id
|
117
|
+
) do |business|
|
118
|
+
business.name = 'Corporate Trading Ltd'
|
119
|
+
business.description = 'Corporate business for trading services'
|
120
|
+
business.contact_email = user3.email
|
121
|
+
business.contact_phone = user3.phone
|
122
|
+
end
|
123
|
+
|
124
|
+
# Create business for user4 (Agent)
|
125
|
+
business4 = Dscf::Core::Business.find_or_create_by(
|
126
|
+
user_id: user4.id,
|
127
|
+
business_type_id: agent_business_type.id
|
128
|
+
) do |business|
|
129
|
+
business.name = 'Financial Agent Services'
|
130
|
+
business.description = 'Agent business for financial services'
|
131
|
+
business.contact_email = user4.email
|
132
|
+
business.contact_phone = user4.phone
|
133
|
+
end
|
134
|
+
|
135
|
+
puts "✓ Businesses created/found"
|
136
|
+
end
|
137
|
+
else
|
138
|
+
puts "Warning: Dscf::Core::User not found. Using placeholder user IDs."
|
139
|
+
admin_user = OpenStruct.new(id: 1)
|
140
|
+
bank_admin = OpenStruct.new(id: 2)
|
141
|
+
user1 = OpenStruct.new(id: 3)
|
142
|
+
user2 = OpenStruct.new(id: 4)
|
143
|
+
user3 = OpenStruct.new(id: 5)
|
144
|
+
user4 = OpenStruct.new(id: 6)
|
145
|
+
end
|
146
|
+
|
147
|
+
# 1. Banks (independent)
|
148
|
+
puts "Seeding banks..."
|
149
|
+
bank1 = Dscf::Credit::Bank.find_or_create_by(registration_number: 'BNK001') do |bank|
|
150
|
+
bank.name = 'Commercial Bank of Ethiopia'
|
151
|
+
bank.swift_code = 'CBETETAA'
|
152
|
+
bank.headquarters_address = 'Addis Ababa, Ethiopia'
|
153
|
+
bank.city = 'Addis Ababa'
|
154
|
+
bank.country = 'Ethiopia'
|
155
|
+
bank.contact_email = 'info@cbe.com.et'
|
156
|
+
bank.contact_phone = '+251115510000'
|
157
|
+
bank.status = 'active'
|
158
|
+
end
|
159
|
+
|
160
|
+
bank2 = Dscf::Credit::Bank.find_or_create_by(registration_number: 'BNK002') do |bank|
|
161
|
+
bank.name = 'Awash Bank'
|
162
|
+
bank.swift_code = 'AWSHETAA'
|
163
|
+
bank.headquarters_address = 'Addis Ababa, Ethiopia'
|
164
|
+
bank.city = 'Addis Ababa'
|
165
|
+
bank.country = 'Ethiopia'
|
166
|
+
bank.contact_email = 'info@awashbank.com'
|
167
|
+
bank.contact_phone = '+251115524000'
|
168
|
+
bank.status = 'active'
|
169
|
+
end
|
170
|
+
|
171
|
+
# 2. Bank Branches (depends on banks)
|
172
|
+
puts "Seeding bank branches..."
|
173
|
+
Dscf::Credit::BankBranch.find_or_create_by(bank: bank1, branch_name: 'Head Office') do |branch|
|
174
|
+
branch.branch_code = 'CBE-HO-001'
|
175
|
+
branch.branch_address = 'Churchill Avenue, Addis Ababa'
|
176
|
+
branch.city = 'Addis Ababa'
|
177
|
+
branch.country = 'Ethiopia'
|
178
|
+
branch.contact_email = 'headoffice@cbe.com.et'
|
179
|
+
branch.contact_phone = '+251115510001'
|
180
|
+
branch.status = 'active'
|
181
|
+
end
|
182
|
+
|
183
|
+
Dscf::Credit::BankBranch.find_or_create_by(bank: bank1, branch_name: 'Merkato Branch') do |branch|
|
184
|
+
branch.branch_code = 'CBE-MER-002'
|
185
|
+
branch.branch_address = 'Merkato, Addis Ababa'
|
186
|
+
branch.city = 'Addis Ababa'
|
187
|
+
branch.country = 'Ethiopia'
|
188
|
+
branch.contact_email = 'merkato@cbe.com.et'
|
189
|
+
branch.contact_phone = '+251115510002'
|
190
|
+
branch.status = 'active'
|
191
|
+
end
|
192
|
+
|
193
|
+
Dscf::Credit::BankBranch.find_or_create_by(bank: bank2, branch_name: 'Main Branch') do |branch|
|
194
|
+
branch.branch_code = 'AWB-MN-001'
|
195
|
+
branch.branch_address = 'Ras Desta Damtew Avenue, Addis Ababa'
|
196
|
+
branch.city = 'Addis Ababa'
|
197
|
+
branch.country = 'Ethiopia'
|
198
|
+
branch.contact_email = 'main@awashbank.com'
|
199
|
+
branch.contact_phone = '+251115524001'
|
200
|
+
branch.status = 'active'
|
201
|
+
end
|
202
|
+
|
203
|
+
# 3. Bank Staff (depends on bank branches and users from dscf-core)
|
204
|
+
puts "Seeding bank staff..."
|
205
|
+
|
206
|
+
# Get bank branches
|
207
|
+
cbe_main_branch = Dscf::Credit::BankBranch.find_by(bank: bank1, branch_name: 'Main Branch')
|
208
|
+
cbe_merkato_branch = Dscf::Credit::BankBranch.find_by(bank: bank1, branch_name: 'Merkato Branch')
|
209
|
+
awash_main_branch = Dscf::Credit::BankBranch.find_by(bank: bank2, branch_name: 'Main Branch')
|
210
|
+
|
211
|
+
# Create bank staff only if we have users from dscf-core
|
212
|
+
if defined?(Dscf::Core::User) && Dscf::Core::User.exists?
|
213
|
+
users = Dscf::Core::User.limit(6)
|
214
|
+
|
215
|
+
# CBE Main Branch Staff
|
216
|
+
if cbe_main_branch && users.first
|
217
|
+
Dscf::Credit::BankStaff.find_or_create_by(
|
218
|
+
user: users.first,
|
219
|
+
bank_branch: cbe_main_branch
|
220
|
+
) do |staff|
|
221
|
+
staff.status = 'active'
|
222
|
+
end
|
223
|
+
end
|
224
|
+
|
225
|
+
if cbe_main_branch && users.second
|
226
|
+
Dscf::Credit::BankStaff.find_or_create_by(
|
227
|
+
user: users.second,
|
228
|
+
bank_branch: cbe_main_branch
|
229
|
+
) do |staff|
|
230
|
+
staff.status = 'active'
|
231
|
+
end
|
232
|
+
end
|
233
|
+
|
234
|
+
# CBE Merkato Branch Staff
|
235
|
+
if cbe_merkato_branch && users.third
|
236
|
+
Dscf::Credit::BankStaff.find_or_create_by(
|
237
|
+
user: users.third,
|
238
|
+
bank_branch: cbe_merkato_branch
|
239
|
+
) do |staff|
|
240
|
+
staff.status = 'active'
|
241
|
+
end
|
242
|
+
end
|
243
|
+
|
244
|
+
if cbe_merkato_branch && users.fourth
|
245
|
+
Dscf::Credit::BankStaff.find_or_create_by(
|
246
|
+
user: users.fourth,
|
247
|
+
bank_branch: cbe_merkato_branch
|
248
|
+
) do |staff|
|
249
|
+
staff.status = 'active'
|
250
|
+
end
|
251
|
+
end
|
252
|
+
|
253
|
+
# Awash Bank Main Branch Staff
|
254
|
+
if awash_main_branch && users.fifth
|
255
|
+
Dscf::Credit::BankStaff.find_or_create_by(
|
256
|
+
user: users.fifth,
|
257
|
+
bank_branch: awash_main_branch
|
258
|
+
) do |staff|
|
259
|
+
staff.status = 'active'
|
260
|
+
end
|
261
|
+
end
|
262
|
+
|
263
|
+
if awash_main_branch && users[5]
|
264
|
+
Dscf::Credit::BankStaff.find_or_create_by(
|
265
|
+
user: users[5],
|
266
|
+
bank_branch: awash_main_branch
|
267
|
+
) do |staff|
|
268
|
+
staff.status = 'active'
|
269
|
+
end
|
270
|
+
end
|
271
|
+
else
|
272
|
+
puts " Skipping bank staff creation - no users found from dscf-core"
|
273
|
+
end
|
274
|
+
|
275
|
+
# 4. System Config Definitions (depends on banks)
|
276
|
+
puts "Seeding system config definitions..."
|
277
|
+
config_def1 = Dscf::Credit::SystemConfigDefinition.find_or_create_by(
|
278
|
+
bank: bank1,
|
279
|
+
config_key: 'max_loan_amount'
|
280
|
+
) do |config|
|
281
|
+
config.description = 'Maximum loan amount allowed per transaction'
|
282
|
+
config.value_type = 'decimal'
|
283
|
+
config.frequency = 'monthly'
|
284
|
+
end
|
285
|
+
|
286
|
+
config_def2 = Dscf::Credit::SystemConfigDefinition.find_or_create_by(
|
287
|
+
bank: bank1,
|
288
|
+
config_key: 'interest_calculation_method'
|
289
|
+
) do |config|
|
290
|
+
config.description = 'Method used for calculating interest'
|
291
|
+
config.value_type = 'string'
|
292
|
+
config.frequency = 'quarterly'
|
293
|
+
end
|
294
|
+
|
295
|
+
config_def3 = Dscf::Credit::SystemConfigDefinition.find_or_create_by(
|
296
|
+
bank: bank2,
|
297
|
+
config_key: 'max_loan_term_days'
|
298
|
+
) do |config|
|
299
|
+
config.description = 'Maximum loan term in days'
|
300
|
+
config.value_type = 'integer'
|
301
|
+
config.frequency = 'yearly'
|
302
|
+
end
|
303
|
+
|
304
|
+
# 4. System Configs (depends on system config definitions)
|
305
|
+
puts "Seeding system configs..."
|
306
|
+
Dscf::Credit::SystemConfig.find_or_create_by(config_definition: config_def1) do |config|
|
307
|
+
config.config_value = '500000.00'
|
308
|
+
config.status = 'approved'
|
309
|
+
config.approved_by = admin_user
|
310
|
+
config.last_updated_by = admin_user
|
311
|
+
end
|
312
|
+
|
313
|
+
Dscf::Credit::SystemConfig.find_or_create_by(config_definition: config_def2) do |config|
|
314
|
+
config.config_value = 'daily'
|
315
|
+
config.status = 'approved'
|
316
|
+
config.approved_by = admin_user
|
317
|
+
config.last_updated_by = admin_user
|
318
|
+
end
|
319
|
+
|
320
|
+
Dscf::Credit::SystemConfig.find_or_create_by(config_definition: config_def3) do |config|
|
321
|
+
config.config_value = '180'
|
322
|
+
config.status = 'pending'
|
323
|
+
config.last_updated_by = bank_admin
|
324
|
+
end
|
325
|
+
|
326
|
+
# 4.5. Categories (independent)
|
327
|
+
puts "Seeding categories..."
|
328
|
+
sme_category = Dscf::Credit::Category.find_or_create_by(type: 'credit_line', name: 'SME') do |category|
|
329
|
+
category.description = 'Small and Medium Enterprise credit category'
|
330
|
+
end
|
331
|
+
|
332
|
+
personal_category = Dscf::Credit::Category.find_or_create_by(type: 'credit_line', name: 'Personal') do |category|
|
333
|
+
category.description = 'Personal credit category for individuals'
|
334
|
+
end
|
335
|
+
|
336
|
+
agricultural_category = Dscf::Credit::Category.find_or_create_by(type: 'credit_line', name: 'Agricultural') do |category|
|
337
|
+
category.description = 'Agricultural sector credit category'
|
338
|
+
end
|
339
|
+
|
340
|
+
corporate_category = Dscf::Credit::Category.find_or_create_by(type: 'credit_line', name: 'Corporate') do |category|
|
341
|
+
category.description = 'Corporate credit category for large businesses'
|
342
|
+
end
|
343
|
+
|
344
|
+
# 5. Credit Lines (depends on banks, users, and categories)
|
345
|
+
puts "Seeding credit lines..."
|
346
|
+
credit_line1 = Dscf::Credit::CreditLine.find_or_create_by(bank: bank1, name: 'SME Credit Line') do |line|
|
347
|
+
line.category = sme_category
|
348
|
+
line.code = 'CBE-SME-001'
|
349
|
+
line.description = 'Credit line for Small and Medium Enterprises'
|
350
|
+
line.status = 'approved'
|
351
|
+
line.created_by = admin_user
|
352
|
+
line.approved_by = bank_admin
|
353
|
+
line.approval_date = 1.week.ago
|
354
|
+
end
|
355
|
+
|
356
|
+
credit_line2 = Dscf::Credit::CreditLine.find_or_create_by(bank: bank1, name: 'Personal Credit Line') do |line|
|
357
|
+
line.category = personal_category
|
358
|
+
line.code = 'CBE-PER-002'
|
359
|
+
line.description = 'Personal credit line for individuals'
|
360
|
+
line.status = 'approved'
|
361
|
+
line.created_by = admin_user
|
362
|
+
line.approved_by = bank_admin
|
363
|
+
line.approval_date = 5.days.ago
|
364
|
+
end
|
365
|
+
|
366
|
+
Dscf::Credit::CreditLine.find_or_create_by(bank: bank2, name: 'Agricultural Credit Line') do |line|
|
367
|
+
line.category = agricultural_category
|
368
|
+
line.code = 'AWB-AGR-001'
|
369
|
+
line.description = 'Credit line for agricultural sector'
|
370
|
+
line.status = 'pending'
|
371
|
+
line.created_by = bank_admin
|
372
|
+
line.approved_by = admin_user
|
373
|
+
end
|
374
|
+
|
375
|
+
# 6. Credit Line Specs (depends on credit lines)
|
376
|
+
puts "Seeding credit line specs..."
|
377
|
+
Dscf::Credit::CreditLineSpec.find_or_create_by(credit_line: credit_line1) do |spec|
|
378
|
+
spec.min_amount = 10000.00
|
379
|
+
spec.max_amount = 500000.00
|
380
|
+
spec.interest_rate = 0.15
|
381
|
+
spec.penalty_rate = 0.02
|
382
|
+
spec.facilitation_fee_rate = 0.01
|
383
|
+
spec.tax_rate = 0.05
|
384
|
+
spec.max_penalty_days = 30
|
385
|
+
spec.loan_duration = 180
|
386
|
+
spec.interest_frequency = 'monthly'
|
387
|
+
spec.interest_income_tax = 0.03
|
388
|
+
spec.vat = 0.15
|
389
|
+
spec.max_interest_calculation_days = 365
|
390
|
+
spec.penalty_frequency = 'weekly'
|
391
|
+
spec.penalty_income_tax = 0.025
|
392
|
+
spec.active = true
|
393
|
+
spec.created_by = admin_user
|
394
|
+
end
|
395
|
+
|
396
|
+
Dscf::Credit::CreditLineSpec.find_or_create_by(credit_line: credit_line2) do |spec|
|
397
|
+
spec.min_amount = 5000.00
|
398
|
+
spec.max_amount = 100000.00
|
399
|
+
spec.interest_rate = 0.18
|
400
|
+
spec.penalty_rate = 0.025
|
401
|
+
spec.facilitation_fee_rate = 0.015
|
402
|
+
spec.tax_rate = 0.05
|
403
|
+
spec.max_penalty_days = 15
|
404
|
+
spec.loan_duration = 90
|
405
|
+
spec.interest_frequency = 'weekly'
|
406
|
+
spec.interest_income_tax = 0.035
|
407
|
+
spec.vat = 0.15
|
408
|
+
spec.max_interest_calculation_days = 180
|
409
|
+
spec.penalty_frequency = 'daily'
|
410
|
+
spec.penalty_income_tax = 0.03
|
411
|
+
spec.active = true
|
412
|
+
spec.created_by = admin_user
|
413
|
+
end
|
414
|
+
|
415
|
+
# 7. Scoring Parameters (depends on banks)
|
416
|
+
puts "Seeding scoring parameters..."
|
417
|
+
scoring_param1 = Dscf::Credit::ScoringParameter.find_or_create_by(
|
418
|
+
bank: bank1,
|
419
|
+
name: 'Monthly Income'
|
420
|
+
) do |param|
|
421
|
+
param.description = 'Monthly income of the applicant'
|
422
|
+
param.data_type = 'decimal'
|
423
|
+
param.type = 'financial'
|
424
|
+
param.weight = 0.3
|
425
|
+
param.min_value = 0
|
426
|
+
param.max_value = 1000000
|
427
|
+
param.active = true
|
428
|
+
param.approved_by = admin_user
|
429
|
+
param.created_by = admin_user
|
430
|
+
param.expires_at = 1.year.from_now
|
431
|
+
end
|
432
|
+
|
433
|
+
scoring_param2 = Dscf::Credit::ScoringParameter.find_or_create_by(
|
434
|
+
bank: bank1,
|
435
|
+
name: 'Credit History Score'
|
436
|
+
) do |param|
|
437
|
+
param.description = 'Credit history score from credit bureau'
|
438
|
+
param.data_type = 'integer'
|
439
|
+
param.type = 'credit_history'
|
440
|
+
param.weight = 0.4
|
441
|
+
param.min_value = 300
|
442
|
+
param.max_value = 850
|
443
|
+
param.active = true
|
444
|
+
param.approved_by = admin_user
|
445
|
+
param.created_by = admin_user
|
446
|
+
param.expires_at = 1.year.from_now
|
447
|
+
end
|
448
|
+
|
449
|
+
scoring_param3 = Dscf::Credit::ScoringParameter.find_or_create_by(
|
450
|
+
bank: bank1,
|
451
|
+
name: 'Employment Type'
|
452
|
+
) do |param|
|
453
|
+
param.description = 'Type of employment (permanent, contract, self-employed)'
|
454
|
+
param.data_type = 'string'
|
455
|
+
param.type = 'employment'
|
456
|
+
param.weight = 0.2
|
457
|
+
param.active = true
|
458
|
+
param.approved_by = bank_admin
|
459
|
+
param.created_by = admin_user
|
460
|
+
param.expires_at = 1.year.from_now
|
461
|
+
end
|
462
|
+
|
463
|
+
# 8. Parameter Normalizers (depends on scoring parameters)
|
464
|
+
puts "Seeding parameter normalizers..."
|
465
|
+
# Ensure we have the scoring parameter reference
|
466
|
+
employment_param = Dscf::Credit::ScoringParameter.find_by(bank: bank1, name: 'Employment Type')
|
467
|
+
|
468
|
+
Dscf::Credit::ParameterNormalizer.find_or_create_by(
|
469
|
+
scoring_parameter: employment_param,
|
470
|
+
raw_value: 'permanent'
|
471
|
+
) do |normalizer|
|
472
|
+
normalizer.name = 'Permanent Employment'
|
473
|
+
normalizer.description = 'Full-time permanent employment'
|
474
|
+
normalizer.normalized_value = 100
|
475
|
+
end
|
476
|
+
|
477
|
+
Dscf::Credit::ParameterNormalizer.find_or_create_by(
|
478
|
+
scoring_parameter: employment_param,
|
479
|
+
raw_value: 'contract'
|
480
|
+
) do |normalizer|
|
481
|
+
normalizer.name = 'Contract Employment'
|
482
|
+
normalizer.description = 'Contract-based employment'
|
483
|
+
normalizer.normalized_value = 70
|
484
|
+
end
|
485
|
+
|
486
|
+
Dscf::Credit::ParameterNormalizer.find_or_create_by(
|
487
|
+
scoring_parameter: employment_param,
|
488
|
+
raw_value: 'self_employed'
|
489
|
+
) do |normalizer|
|
490
|
+
normalizer.name = 'Self Employed'
|
491
|
+
normalizer.description = 'Self-employed individual'
|
492
|
+
normalizer.normalized_value = 60
|
493
|
+
end
|
494
|
+
|
495
|
+
# 8.5. Scoring Tables (depends on credit lines and scoring parameters)
|
496
|
+
puts "Seeding scoring tables..."
|
497
|
+
# Get references to scoring parameters
|
498
|
+
monthly_income_param = Dscf::Credit::ScoringParameter.find_by(bank: bank1, name: 'Monthly Income')
|
499
|
+
credit_history_param = Dscf::Credit::ScoringParameter.find_by(bank: bank1, name: 'Credit History Score')
|
500
|
+
employment_param = Dscf::Credit::ScoringParameter.find_by(bank: bank1, name: 'Employment Type')
|
501
|
+
|
502
|
+
# Create scoring tables for credit_line1 (SME Credit Line)
|
503
|
+
if monthly_income_param
|
504
|
+
Dscf::Credit::ScoringTable.find_or_create_by(
|
505
|
+
credit_line: credit_line1,
|
506
|
+
scoring_parameter: monthly_income_param
|
507
|
+
) do |scoring_table|
|
508
|
+
scoring_table.weight = 0.4
|
509
|
+
scoring_table.active = true
|
510
|
+
scoring_table.created_by = admin_user
|
511
|
+
end
|
512
|
+
end
|
513
|
+
|
514
|
+
if credit_history_param
|
515
|
+
Dscf::Credit::ScoringTable.find_or_create_by(
|
516
|
+
credit_line: credit_line1,
|
517
|
+
scoring_parameter: credit_history_param
|
518
|
+
) do |scoring_table|
|
519
|
+
scoring_table.weight = 0.35
|
520
|
+
scoring_table.active = true
|
521
|
+
scoring_table.created_by = admin_user
|
522
|
+
end
|
523
|
+
end
|
524
|
+
|
525
|
+
if employment_param
|
526
|
+
Dscf::Credit::ScoringTable.find_or_create_by(
|
527
|
+
credit_line: credit_line1,
|
528
|
+
scoring_parameter: employment_param
|
529
|
+
) do |scoring_table|
|
530
|
+
scoring_table.weight = 0.25
|
531
|
+
scoring_table.active = true
|
532
|
+
scoring_table.created_by = admin_user
|
533
|
+
end
|
534
|
+
end
|
535
|
+
|
536
|
+
# Create scoring tables for credit_line2 (Personal Credit Line)
|
537
|
+
if monthly_income_param
|
538
|
+
Dscf::Credit::ScoringTable.find_or_create_by(
|
539
|
+
credit_line: credit_line2,
|
540
|
+
scoring_parameter: monthly_income_param
|
541
|
+
) do |scoring_table|
|
542
|
+
scoring_table.weight = 0.5
|
543
|
+
scoring_table.active = true
|
544
|
+
scoring_table.created_by = admin_user
|
545
|
+
end
|
546
|
+
end
|
547
|
+
|
548
|
+
if credit_history_param
|
549
|
+
Dscf::Credit::ScoringTable.find_or_create_by(
|
550
|
+
credit_line: credit_line2,
|
551
|
+
scoring_parameter: credit_history_param
|
552
|
+
) do |scoring_table|
|
553
|
+
scoring_table.weight = 0.3
|
554
|
+
scoring_table.active = true
|
555
|
+
scoring_table.created_by = admin_user
|
556
|
+
end
|
557
|
+
end
|
558
|
+
|
559
|
+
if employment_param
|
560
|
+
Dscf::Credit::ScoringTable.find_or_create_by(
|
561
|
+
credit_line: credit_line2,
|
562
|
+
scoring_parameter: employment_param
|
563
|
+
) do |scoring_table|
|
564
|
+
scoring_table.weight = 0.2
|
565
|
+
scoring_table.active = true
|
566
|
+
scoring_table.created_by = admin_user
|
567
|
+
end
|
568
|
+
end
|
569
|
+
|
570
|
+
# 9. Loan Profiles (depends on banks and users)
|
571
|
+
puts "Seeding loan profiles..."
|
572
|
+
loan_profile1 = Dscf::Credit::LoanProfile.find_or_create_by(
|
573
|
+
bank: bank1,
|
574
|
+
user: user2
|
575
|
+
) do |profile|
|
576
|
+
profile.status = 'approved'
|
577
|
+
profile.total_amount = 100000.00
|
578
|
+
profile.available_amount = 75000.00
|
579
|
+
profile.approved_by = bank_admin
|
580
|
+
# Note: backer will be set when facilitators are created via API
|
581
|
+
end
|
582
|
+
|
583
|
+
# 12. Loan Profile Scoring Specs (depends on loan profiles)
|
584
|
+
puts "Seeding loan profile scoring specs..."
|
585
|
+
Dscf::Credit::LoanProfileScoringSpec.create!(
|
586
|
+
loan_profile: loan_profile1,
|
587
|
+
scoring_input_data: {
|
588
|
+
'monthly_income' => 45000,
|
589
|
+
'credit_history_score' => 720,
|
590
|
+
'employment_type' => 'permanent',
|
591
|
+
'years_at_job' => 3,
|
592
|
+
'existing_debt' => 15000
|
593
|
+
},
|
594
|
+
score: 78.5,
|
595
|
+
active: true,
|
596
|
+
approved_by: admin_user,
|
597
|
+
created_by: admin_user,
|
598
|
+
expires_at: 6.months.from_now
|
599
|
+
)
|
600
|
+
|
601
|
+
# 13. Payment Requests (depends on users)
|
602
|
+
puts "Seeding payment requests..."
|
603
|
+
payment_request1 = Dscf::Credit::PaymentRequest.create!(
|
604
|
+
user: user2,
|
605
|
+
order_id: "ORD-#{Time.current.to_i}-001",
|
606
|
+
request_type: 'loan_disbursement',
|
607
|
+
amount: 50000.00,
|
608
|
+
receiver_account_reference: 'ACC-BORROWER-001',
|
609
|
+
status: 'approved',
|
610
|
+
initiated_at: 2.days.ago,
|
611
|
+
approved_at: 1.day.ago
|
612
|
+
)
|
613
|
+
|
614
|
+
payment_request2 = Dscf::Credit::PaymentRequest.create!(
|
615
|
+
user: user2,
|
616
|
+
order_id: "ORD-#{Time.current.to_i}-002",
|
617
|
+
request_type: 'loan_repayment',
|
618
|
+
amount: 15000.00,
|
619
|
+
receiver_account_reference: 'ACC-BANK-001',
|
620
|
+
status: 'pending',
|
621
|
+
initiated_at: 1.hour.ago
|
622
|
+
)
|
623
|
+
|
624
|
+
# 14. Loans (depends on loan profiles, credit lines, and payment requests)
|
625
|
+
puts "Seeding loans..."
|
626
|
+
loan1 = Dscf::Credit::Loan.create!(
|
627
|
+
loan_profile: loan_profile1,
|
628
|
+
credit_line: credit_line1,
|
629
|
+
payment_request: payment_request1,
|
630
|
+
status: 'active',
|
631
|
+
principal_amount: 50000.00,
|
632
|
+
accrued_interest: 2500.00,
|
633
|
+
accrued_penalty: 0.00,
|
634
|
+
facilitation_fee: 1000.00,
|
635
|
+
total_loan_amount: 53500.00,
|
636
|
+
remaining_amount: 53500.00,
|
637
|
+
due_date: 3.months.from_now.to_date,
|
638
|
+
disbursed_at: 1.day.ago
|
639
|
+
)
|
640
|
+
|
641
|
+
# 15. Loan Transactions (depends on loans)
|
642
|
+
puts "Seeding loan transactions..."
|
643
|
+
Dscf::Credit::LoanTransaction.create!(
|
644
|
+
loan: loan1,
|
645
|
+
transaction_type: 'disbursement',
|
646
|
+
amount: 50000.00,
|
647
|
+
transaction_reference: "TXN-DISB-#{Time.current.to_i}",
|
648
|
+
status: 'completed'
|
649
|
+
)
|
650
|
+
|
651
|
+
Dscf::Credit::LoanTransaction.create!(
|
652
|
+
loan: loan1,
|
653
|
+
transaction_type: 'interest_accrual',
|
654
|
+
amount: 2500.00,
|
655
|
+
transaction_reference: "TXN-INT-#{Time.current.to_i}",
|
656
|
+
status: 'completed'
|
657
|
+
)
|
658
|
+
|
659
|
+
# 16. Daily Routine Transactions (depends on loans)
|
660
|
+
puts "Seeding daily routine transactions..."
|
661
|
+
Dscf::Credit::DailyRoutineTransaction.create!(
|
662
|
+
loan: loan1,
|
663
|
+
routine_type: 'interest_calculation',
|
664
|
+
amount: 83.33,
|
665
|
+
status: 'completed',
|
666
|
+
initiated_at: Date.current.beginning_of_day,
|
667
|
+
approved_at: Date.current.beginning_of_day + 1.hour
|
668
|
+
)
|
669
|
+
|
670
|
+
# 17. Payments (depends on payment requests)
|
671
|
+
puts "Seeding payments..."
|
672
|
+
Dscf::Credit::Payment.create!(
|
673
|
+
payment_request: payment_request1,
|
674
|
+
amount: 50000.00,
|
675
|
+
receiver_account_reference: 'ACC-BORROWER-001',
|
676
|
+
transaction_reference: "PAY-#{Time.current.to_i}-001",
|
677
|
+
status: 'completed',
|
678
|
+
processed_at: 1.day.ago
|
679
|
+
)
|
680
|
+
|
681
|
+
# 18. Accounting Audit Requests (depends on various entities)
|
682
|
+
puts "Seeding accounting audit requests..."
|
683
|
+
audit_request1 = Dscf::Credit::AccountingAuditRequest.create!(
|
684
|
+
source_entity: loan1,
|
685
|
+
transaction_type: 'debit',
|
686
|
+
amount: 50000.00,
|
687
|
+
webhook_key: "WEBHOOK-#{SecureRandom.hex(16)}",
|
688
|
+
status: 'completed'
|
689
|
+
)
|
690
|
+
|
691
|
+
Dscf::Credit::AccountingAuditRequest.create!(
|
692
|
+
source_entity: payment_request1,
|
693
|
+
transaction_type: 'transfer',
|
694
|
+
amount: 50000.00,
|
695
|
+
webhook_key: "WEBHOOK-#{SecureRandom.hex(16)}",
|
696
|
+
status: 'pending'
|
697
|
+
)
|
698
|
+
|
699
|
+
# 19. Accounting Entries (depends on audit requests)
|
700
|
+
puts "Seeding accounting entries..."
|
701
|
+
Dscf::Credit::AccountingEntry.create!(
|
702
|
+
audit_request: audit_request1,
|
703
|
+
account_code: 'LOAN_ASSET_001',
|
704
|
+
entry_type: 'debit',
|
705
|
+
amount: 50000.00,
|
706
|
+
status: 'completed'
|
707
|
+
)
|
708
|
+
|
709
|
+
Dscf::Credit::AccountingEntry.create!(
|
710
|
+
audit_request: audit_request1,
|
711
|
+
account_code: 'CASH_001',
|
712
|
+
entry_type: 'credit',
|
713
|
+
amount: 50000.00,
|
714
|
+
status: 'completed'
|
715
|
+
)
|
716
|
+
|
717
|
+
# 20. Failed Operations Logs (depends on various entities)
|
718
|
+
puts "Seeding failed operations logs..."
|
719
|
+
Dscf::Credit::FailedOperationsLog.create!(
|
720
|
+
entity: payment_request2,
|
721
|
+
failure_type: 'payment_processing',
|
722
|
+
reason: 'Payment gateway did not respond within timeout period',
|
723
|
+
retry_count: 2,
|
724
|
+
resolved: false
|
725
|
+
)
|
726
|
+
|
727
|
+
puts "DSCF Credit Engine seed data completed successfully!"
|
728
|
+
puts "Created sample data for all models with proper relationships."
|
729
|
+
puts "Summary:"
|
730
|
+
puts "- Users: #{Dscf::Core::User.count}"
|
731
|
+
puts "- Business Types: #{Dscf::Core::BusinessType.count}"
|
732
|
+
puts "- Businesses: #{Dscf::Core::Business.count}"
|
733
|
+
puts "- Banks: #{Dscf::Credit::Bank.count}"
|
734
|
+
puts "- Bank Branches: #{Dscf::Credit::BankBranch.count}"
|
735
|
+
puts "- Bank Staff: #{Dscf::Credit::BankStaff.count}"
|
736
|
+
puts "- Categories: #{Dscf::Credit::Category.count}"
|
737
|
+
puts "- Credit Lines: #{Dscf::Credit::CreditLine.count}"
|
738
|
+
puts "- Loan Profiles: #{Dscf::Credit::LoanProfile.count}"
|
739
|
+
puts "- Loans: #{Dscf::Credit::Loan.count}"
|
740
|
+
puts "- Payment Requests: #{Dscf::Credit::PaymentRequest.count}"
|
741
|
+
puts "- Payments: #{Dscf::Credit::Payment.count}"
|
742
|
+
puts "- Facilitators: #{Dscf::Credit::Facilitator.count} (will be created via API)"
|
743
|
+
puts "- System Configs: #{Dscf::Credit::SystemConfig.count}"
|
744
|
+
puts "- Scoring Parameters: #{Dscf::Credit::ScoringParameter.count}"
|
745
|
+
puts "- Scoring Tables: #{Dscf::Credit::ScoringTable.count}"
|