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
@@ -0,0 +1,99 @@
|
|
1
|
+
module Dscf::Credit
|
2
|
+
class BankStaffCreationService
|
3
|
+
include ActiveModel::Model
|
4
|
+
include ActiveModel::Attributes
|
5
|
+
|
6
|
+
# User attributes
|
7
|
+
attribute :email, :string
|
8
|
+
attribute :phone, :string
|
9
|
+
attribute :first_name, :string
|
10
|
+
attribute :middle_name, :string
|
11
|
+
attribute :last_name, :string
|
12
|
+
attribute :position_title, :string
|
13
|
+
attribute :gender, :string
|
14
|
+
|
15
|
+
# Staff attributes
|
16
|
+
attribute :bank_branch_id, :integer
|
17
|
+
attribute :status, :string, default: "active"
|
18
|
+
|
19
|
+
# Role attributes
|
20
|
+
attribute :role_code, :string
|
21
|
+
|
22
|
+
validates :email, presence: true, format: { with: URI::MailTo::EMAIL_REGEXP }
|
23
|
+
validates :phone, presence: true
|
24
|
+
validates :first_name, :last_name, presence: true
|
25
|
+
validates :bank_branch_id, presence: true
|
26
|
+
validates :role_code, presence: true
|
27
|
+
|
28
|
+
attr_reader :user, :bank_staff, :generated_password
|
29
|
+
|
30
|
+
def initialize(attributes = {})
|
31
|
+
super(attributes)
|
32
|
+
end
|
33
|
+
|
34
|
+
def call
|
35
|
+
ActiveRecord::Base.transaction do
|
36
|
+
create_user!
|
37
|
+
assign_role!
|
38
|
+
create_bank_staff!
|
39
|
+
send_welcome_email!
|
40
|
+
|
41
|
+
true
|
42
|
+
rescue => e
|
43
|
+
errors.add(:base, e.message)
|
44
|
+
false
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
private
|
49
|
+
|
50
|
+
def create_user!
|
51
|
+
@generated_password = generate_secure_password
|
52
|
+
|
53
|
+
@user = Dscf::Core::User.create!(
|
54
|
+
email: email,
|
55
|
+
phone: phone,
|
56
|
+
password: @generated_password,
|
57
|
+
temp_password: true,
|
58
|
+
verified_at: nil
|
59
|
+
)
|
60
|
+
|
61
|
+
profile_attrs = {
|
62
|
+
first_name: first_name,
|
63
|
+
middle_name: middle_name,
|
64
|
+
last_name: last_name,
|
65
|
+
position_title: position_title,
|
66
|
+
gender: gender,
|
67
|
+
verification_status: "pending"
|
68
|
+
}
|
69
|
+
|
70
|
+
@user.create_user_profile!(profile_attrs)
|
71
|
+
end
|
72
|
+
|
73
|
+
def assign_role!
|
74
|
+
role = Dscf::Core::Role.find_by!(code: role_code)
|
75
|
+
|
76
|
+
Dscf::Core::UserRole.create!(
|
77
|
+
user: @user,
|
78
|
+
role: role
|
79
|
+
)
|
80
|
+
end
|
81
|
+
|
82
|
+
def create_bank_staff!
|
83
|
+
@bank_staff = Dscf::Credit::BankStaff.create!(
|
84
|
+
user: @user,
|
85
|
+
bank_branch_id: bank_branch_id,
|
86
|
+
status: status
|
87
|
+
)
|
88
|
+
end
|
89
|
+
|
90
|
+
def send_welcome_email!
|
91
|
+
BankStaffWelcomeMailer.welcome_email(@user, @generated_password, @bank_staff).deliver_now
|
92
|
+
end
|
93
|
+
|
94
|
+
def generate_secure_password
|
95
|
+
charset = Array("A".."Z") + Array("a".."z") + Array("0".."9") + [ "!", "@", "#", "$", "%" ]
|
96
|
+
Array.new(12) { charset.sample }.join
|
97
|
+
end
|
98
|
+
end
|
99
|
+
end
|
@@ -0,0 +1,62 @@
|
|
1
|
+
module Dscf::Credit
|
2
|
+
class FacilitatorAdditionalInfoService
|
3
|
+
def submit_info(token, additional_info)
|
4
|
+
payload = verify_token(token)
|
5
|
+
|
6
|
+
facilitator_id = payload["facilitator_id"]
|
7
|
+
|
8
|
+
facilitator = Dscf::Credit::Facilitator.find(facilitator_id)
|
9
|
+
|
10
|
+
performance = facilitator.facilitator_performances.current.first
|
11
|
+
|
12
|
+
if performance&.input_data&.present? && performance.input_data["additional_info_submitted"]
|
13
|
+
raise StandardError, "Additional information has already been submitted for this facilitator"
|
14
|
+
end
|
15
|
+
|
16
|
+
if performance
|
17
|
+
updated_data = performance.input_data || {}
|
18
|
+
updated_data.merge!(additional_info)
|
19
|
+
updated_data["additional_info_submitted"] = true
|
20
|
+
updated_data["submission_date"] = Time.current.iso8601
|
21
|
+
|
22
|
+
performance.update!(
|
23
|
+
input_data: updated_data,
|
24
|
+
updated_at: Time.current
|
25
|
+
)
|
26
|
+
else
|
27
|
+
input_data = additional_info.dup
|
28
|
+
input_data["additional_info_submitted"] = true
|
29
|
+
input_data["submission_date"] = Time.current.iso8601
|
30
|
+
|
31
|
+
performance = facilitator.facilitator_performances.create!(
|
32
|
+
total_outstanding_loans: 0,
|
33
|
+
total_outstanding_amount: 0.0,
|
34
|
+
approval_required: false,
|
35
|
+
input_data: input_data,
|
36
|
+
created_by_type: "System",
|
37
|
+
created_by_id: nil
|
38
|
+
)
|
39
|
+
end
|
40
|
+
|
41
|
+
begin
|
42
|
+
FacilitatorMailer.additional_info_received(facilitator).deliver_now
|
43
|
+
rescue => e
|
44
|
+
Rails.logger.error "Failed to send additional info confirmation email: #{e.message}"
|
45
|
+
end
|
46
|
+
|
47
|
+
{
|
48
|
+
facilitator: facilitator,
|
49
|
+
performance: performance,
|
50
|
+
message: "Additional information submitted successfully"
|
51
|
+
}
|
52
|
+
end
|
53
|
+
|
54
|
+
private
|
55
|
+
|
56
|
+
def verify_token(token)
|
57
|
+
Rails.application.message_verifier("additional_info").verify(token)
|
58
|
+
rescue ActiveSupport::MessageVerifier::InvalidSignature, ActiveSupport::MessageExpired => e
|
59
|
+
raise StandardError, "Invalid or expired token: #{e.message}"
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
@@ -0,0 +1,88 @@
|
|
1
|
+
module Dscf::Credit
|
2
|
+
class FacilitatorApprovalService
|
3
|
+
attr_reader :facilitator, :approver
|
4
|
+
|
5
|
+
def initialize(facilitator, approver)
|
6
|
+
@facilitator = facilitator
|
7
|
+
@approver = approver
|
8
|
+
end
|
9
|
+
|
10
|
+
def approve(total_limit = nil)
|
11
|
+
ActiveRecord::Base.transaction do
|
12
|
+
facilitator.update!(
|
13
|
+
kyc_status: "approved",
|
14
|
+
kyc_approved_by: approver,
|
15
|
+
total_limit: total_limit
|
16
|
+
)
|
17
|
+
|
18
|
+
token = generate_additional_info_token
|
19
|
+
|
20
|
+
begin
|
21
|
+
FacilitatorMailer.approval_notification(facilitator, token).deliver_now
|
22
|
+
rescue => e
|
23
|
+
Rails.logger.error "Failed to send approval email: #{e.message}"
|
24
|
+
end
|
25
|
+
|
26
|
+
update_facilitator_performance
|
27
|
+
|
28
|
+
facilitator
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
def reject(rejection_reason = nil)
|
33
|
+
ActiveRecord::Base.transaction do
|
34
|
+
facilitator.update!(
|
35
|
+
kyc_status: "rejected",
|
36
|
+
kyc_approved_by: approver
|
37
|
+
)
|
38
|
+
|
39
|
+
begin
|
40
|
+
FacilitatorMailer.rejection_notification(facilitator, rejection_reason).deliver_now
|
41
|
+
rescue => e
|
42
|
+
Rails.logger.error "Failed to send rejection email: #{e.message}"
|
43
|
+
end
|
44
|
+
|
45
|
+
facilitator
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
def set_limit(total_limit)
|
50
|
+
facilitator.update!(total_limit: total_limit)
|
51
|
+
|
52
|
+
begin
|
53
|
+
FacilitatorMailer.limit_update_notification(facilitator).deliver_now
|
54
|
+
rescue => e
|
55
|
+
Rails.logger.error "Failed to send limit update email: #{e.message}"
|
56
|
+
end
|
57
|
+
|
58
|
+
facilitator
|
59
|
+
end
|
60
|
+
|
61
|
+
private
|
62
|
+
|
63
|
+
def generate_additional_info_token
|
64
|
+
payload = {
|
65
|
+
facilitator_id: facilitator.id,
|
66
|
+
purpose: "additional_info",
|
67
|
+
exp: 30.days.from_now.to_i
|
68
|
+
}
|
69
|
+
|
70
|
+
Rails.application.message_verifier("additional_info").generate(payload)
|
71
|
+
end
|
72
|
+
|
73
|
+
def update_facilitator_performance
|
74
|
+
performance = facilitator.facilitator_performances.current.first
|
75
|
+
|
76
|
+
if performance
|
77
|
+
performance.update!(approval_required: false)
|
78
|
+
else
|
79
|
+
facilitator.facilitator_performances.create!(
|
80
|
+
total_outstanding_loans: 0,
|
81
|
+
total_outstanding_amount: 0.0,
|
82
|
+
approval_required: false,
|
83
|
+
created_by: approver
|
84
|
+
)
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
88
|
+
end
|
@@ -0,0 +1,116 @@
|
|
1
|
+
<!DOCTYPE html>
|
2
|
+
<html>
|
3
|
+
<head>
|
4
|
+
<meta charset="utf-8">
|
5
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
6
|
+
<title>Welcome to DSCF Banking System</title>
|
7
|
+
<style>
|
8
|
+
body {
|
9
|
+
font-family: Arial, sans-serif;
|
10
|
+
line-height: 1.6;
|
11
|
+
color: #333;
|
12
|
+
max-width: 600px;
|
13
|
+
margin: 0 auto;
|
14
|
+
padding: 20px;
|
15
|
+
}
|
16
|
+
.header {
|
17
|
+
background-color: #2c3e50;
|
18
|
+
color: white;
|
19
|
+
padding: 20px;
|
20
|
+
text-align: center;
|
21
|
+
border-radius: 5px 5px 0 0;
|
22
|
+
}
|
23
|
+
.content {
|
24
|
+
background-color: #f9f9f9;
|
25
|
+
padding: 30px;
|
26
|
+
border-radius: 0 0 5px 5px;
|
27
|
+
}
|
28
|
+
.credentials-box {
|
29
|
+
background-color: #e8f4f8;
|
30
|
+
border: 1px solid #bee5eb;
|
31
|
+
border-radius: 5px;
|
32
|
+
padding: 15px;
|
33
|
+
margin: 20px 0;
|
34
|
+
}
|
35
|
+
.button {
|
36
|
+
display: inline-block;
|
37
|
+
background-color: #007bff;
|
38
|
+
color: white;
|
39
|
+
padding: 12px 25px;
|
40
|
+
text-decoration: none;
|
41
|
+
border-radius: 5px;
|
42
|
+
margin: 20px 0;
|
43
|
+
}
|
44
|
+
.warning {
|
45
|
+
background-color: #fff3cd;
|
46
|
+
border: 1px solid #ffeaa7;
|
47
|
+
color: #856404;
|
48
|
+
padding: 10px;
|
49
|
+
border-radius: 5px;
|
50
|
+
margin: 15px 0;
|
51
|
+
}
|
52
|
+
.footer {
|
53
|
+
text-align: center;
|
54
|
+
color: #666;
|
55
|
+
font-size: 12px;
|
56
|
+
margin-top: 30px;
|
57
|
+
padding-top: 20px;
|
58
|
+
border-top: 1px solid #eee;
|
59
|
+
}
|
60
|
+
</style>
|
61
|
+
</head>
|
62
|
+
<body>
|
63
|
+
<div class="header">
|
64
|
+
<h1>Welcome to DSCF Banking System</h1>
|
65
|
+
</div>
|
66
|
+
|
67
|
+
<div class="content">
|
68
|
+
<h2>Hello <%= @user.user_profile&.first_name || 'Staff Member' %>!</h2>
|
69
|
+
|
70
|
+
<p>Welcome to the DSCF Banking System. Your bank staff account has been successfully created. Below are your login credentials:</p>
|
71
|
+
|
72
|
+
<div class="credentials-box">
|
73
|
+
<h3>Your Login Credentials:</h3>
|
74
|
+
<p><strong>Email:</strong> <%= @user.email %></p>
|
75
|
+
<p><strong>Phone:</strong> <%= @user.phone %></p>
|
76
|
+
<p><strong>Temporary Password:</strong> <code><%= @generated_password %></code></p>
|
77
|
+
</div>
|
78
|
+
|
79
|
+
<div class="warning">
|
80
|
+
<strong>Important Security Notice:</strong>
|
81
|
+
<ul>
|
82
|
+
<li>This is a temporary password that must be changed upon first login</li>
|
83
|
+
<li>Please keep this information secure and do not share it with anyone</li>
|
84
|
+
<li>Your account will require password change on first access</li>
|
85
|
+
</ul>
|
86
|
+
</div>
|
87
|
+
|
88
|
+
<% if @bank_staff %>
|
89
|
+
<h3>Your Role Information:</h3>
|
90
|
+
<p><strong>Position:</strong> <%= @user.user_profile&.position_title || 'Bank Staff' %></p>
|
91
|
+
<p><strong>Status:</strong> <%= @bank_staff.status.humanize %></p>
|
92
|
+
<p><strong>Bank Branch:</strong> <%= @bank_staff.bank_branch&.branch_name || 'Not specified' %></p>
|
93
|
+
<% end %>
|
94
|
+
|
95
|
+
<h3>Next Steps:</h3>
|
96
|
+
<ol>
|
97
|
+
<li>Click the login button below to access the system</li>
|
98
|
+
<li>Use your email and the temporary password provided above</li>
|
99
|
+
<li>You will be prompted to create a new password</li>
|
100
|
+
<li>Complete your profile information if needed</li>
|
101
|
+
</ol>
|
102
|
+
|
103
|
+
<div style="text-align: center;">
|
104
|
+
<a href="<%= @login_url %>/login" class="button">Login to DSCF System</a>
|
105
|
+
</div>
|
106
|
+
|
107
|
+
<h3>Need Help?</h3>
|
108
|
+
<p>If you have any questions or need assistance, please contact your system administrator or IT support team.</p>
|
109
|
+
</div>
|
110
|
+
|
111
|
+
<div class="footer">
|
112
|
+
<p>This email was automatically generated by the DSCF Banking System.</p>
|
113
|
+
<p>Please do not reply to this email.</p>
|
114
|
+
</div>
|
115
|
+
</body>
|
116
|
+
</html>
|
@@ -0,0 +1,40 @@
|
|
1
|
+
Welcome to DSCF Banking System!
|
2
|
+
|
3
|
+
Hello <%= @user.user_profile&.first_name || 'Staff Member' %>!
|
4
|
+
|
5
|
+
Welcome to the DSCF Banking System. Your bank staff account has been successfully created.
|
6
|
+
|
7
|
+
LOGIN CREDENTIALS:
|
8
|
+
==================
|
9
|
+
Email: <%= @user.email %>
|
10
|
+
Phone: <%= @user.phone %>
|
11
|
+
Temporary Password: <%= @generated_password %>
|
12
|
+
|
13
|
+
IMPORTANT SECURITY NOTICE:
|
14
|
+
=========================
|
15
|
+
- This is a temporary password that must be changed upon first login
|
16
|
+
- Please keep this information secure and do not share it with anyone
|
17
|
+
- Your account will require password change on first access
|
18
|
+
|
19
|
+
<% if @bank_staff %>
|
20
|
+
YOUR ROLE INFORMATION:
|
21
|
+
=====================
|
22
|
+
Position: <%= @user.user_profile&.position_title || 'Bank Staff' %>
|
23
|
+
Status: <%= @bank_staff.status.humanize %>
|
24
|
+
Bank Branch: <%= @bank_staff.bank_branch&.branch_name || 'Not specified' %>
|
25
|
+
<% end %>
|
26
|
+
|
27
|
+
NEXT STEPS:
|
28
|
+
==========
|
29
|
+
1. Visit the login page: <%= @login_url %>/login
|
30
|
+
2. Use your email and the temporary password provided above
|
31
|
+
3. You will be prompted to create a new password
|
32
|
+
4. Complete your profile information if needed
|
33
|
+
|
34
|
+
NEED HELP?
|
35
|
+
==========
|
36
|
+
If you have any questions or need assistance, please contact your system administrator or IT support team.
|
37
|
+
|
38
|
+
---
|
39
|
+
This email was automatically generated by the DSCF Banking System.
|
40
|
+
Please do not reply to this email.
|
@@ -0,0 +1,39 @@
|
|
1
|
+
<!DOCTYPE html>
|
2
|
+
<html>
|
3
|
+
<head>
|
4
|
+
<meta charset="utf-8">
|
5
|
+
<style>
|
6
|
+
body { font-family: Arial, sans-serif; line-height: 1.6; color: #333; }
|
7
|
+
.container { max-width: 600px; margin: 0 auto; padding: 20px; }
|
8
|
+
.header { background-color: #d1ecf1; padding: 20px; border-radius: 5px; margin-bottom: 20px; }
|
9
|
+
.content { padding: 20px 0; }
|
10
|
+
.footer { margin-top: 30px; padding-top: 20px; border-top: 1px solid #eee; font-size: 12px; color: #666; }
|
11
|
+
</style>
|
12
|
+
</head>
|
13
|
+
<body>
|
14
|
+
<div class="container">
|
15
|
+
<div class="header">
|
16
|
+
<h1>✅ Additional Information Received</h1>
|
17
|
+
</div>
|
18
|
+
|
19
|
+
<div class="content">
|
20
|
+
<p>Dear <%= @merchant.email %>,</p>
|
21
|
+
|
22
|
+
<p>Thank you! We have successfully received your additional information for facilitator <strong><%= @facilitator.name %></strong>.</p>
|
23
|
+
|
24
|
+
<p>Your information is being processed and we'll notify you of any updates or if we need additional details.</p>
|
25
|
+
|
26
|
+
<p>You can now start using your facilitator account to facilitate transactions within your approved credit limit.</p>
|
27
|
+
|
28
|
+
<p>If you have any questions, please contact our support team.</p>
|
29
|
+
|
30
|
+
<p>Best regards,<br>
|
31
|
+
The DSCF Credit Team</p>
|
32
|
+
</div>
|
33
|
+
|
34
|
+
<div class="footer">
|
35
|
+
<p>This is an automated email. Please do not reply to this message.</p>
|
36
|
+
</div>
|
37
|
+
</div>
|
38
|
+
</body>
|
39
|
+
</html>
|
@@ -0,0 +1,17 @@
|
|
1
|
+
Dear <%= @merchant.email %>,
|
2
|
+
|
3
|
+
✅ ADDITIONAL INFORMATION RECEIVED
|
4
|
+
|
5
|
+
Thank you! We have successfully received your additional information for facilitator "<%= @facilitator.name %>".
|
6
|
+
|
7
|
+
Your information is being processed and we'll notify you of any updates or if we need additional details.
|
8
|
+
|
9
|
+
You can now start using your facilitator account to facilitate transactions within your approved credit limit.
|
10
|
+
|
11
|
+
If you have any questions, please contact our support team.
|
12
|
+
|
13
|
+
Best regards,
|
14
|
+
The DSCF Credit Team
|
15
|
+
|
16
|
+
---
|
17
|
+
This is an automated email. Please do not reply to this message.
|
@@ -0,0 +1,59 @@
|
|
1
|
+
<!DOCTYPE html>
|
2
|
+
<html>
|
3
|
+
<head>
|
4
|
+
<meta charset="utf-8">
|
5
|
+
<style>
|
6
|
+
body { font-family: Arial, sans-serif; line-height: 1.6; color: #333; }
|
7
|
+
.container { max-width: 600px; margin: 0 auto; padding: 20px; }
|
8
|
+
.header { background-color: #f8f9fa; padding: 20px; border-radius: 5px; margin-bottom: 20px; }
|
9
|
+
.content { padding: 20px 0; }
|
10
|
+
.button {
|
11
|
+
display: inline-block;
|
12
|
+
padding: 12px 24px;
|
13
|
+
background-color: #007bff;
|
14
|
+
color: white;
|
15
|
+
text-decoration: none;
|
16
|
+
border-radius: 5px;
|
17
|
+
margin: 15px 0;
|
18
|
+
}
|
19
|
+
.footer { margin-top: 30px; padding-top: 20px; border-top: 1px solid #eee; font-size: 12px; color: #666; }
|
20
|
+
</style>
|
21
|
+
</head>
|
22
|
+
<body>
|
23
|
+
<div class="container">
|
24
|
+
<div class="header">
|
25
|
+
<h1>🎉 Facilitator Application Approved!</h1>
|
26
|
+
</div>
|
27
|
+
|
28
|
+
<div class="content">
|
29
|
+
<p>Dear <%= @merchant.email %>,</p>
|
30
|
+
|
31
|
+
<p>Great news! Your facilitator application for <strong><%= @facilitator.name %></strong> has been approved.</p>
|
32
|
+
|
33
|
+
<% if @total_limit %>
|
34
|
+
<p><strong>Approved Credit Limit:</strong> $<%= number_with_delimiter(@total_limit) %></p>
|
35
|
+
<% end %>
|
36
|
+
|
37
|
+
<p>To complete your setup and start facilitating transactions, please submit your additional information by clicking the link below:</p>
|
38
|
+
|
39
|
+
<a href="<%= @additional_info_url %>" class="button">Submit Additional Information</a>
|
40
|
+
|
41
|
+
<p><strong>Important Notes:</strong></p>
|
42
|
+
<ul>
|
43
|
+
<li>This link will expire in 30 days</li>
|
44
|
+
<li>Complete your additional information to activate your facilitator account</li>
|
45
|
+
<li>You'll receive a confirmation once your information is processed</li>
|
46
|
+
</ul>
|
47
|
+
|
48
|
+
<p>If you have any questions, please don't hesitate to contact our support team.</p>
|
49
|
+
|
50
|
+
<p>Best regards,<br>
|
51
|
+
The DSCF Credit Team</p>
|
52
|
+
</div>
|
53
|
+
|
54
|
+
<div class="footer">
|
55
|
+
<p>This is an automated email. Please do not reply to this message.</p>
|
56
|
+
</div>
|
57
|
+
</div>
|
58
|
+
</body>
|
59
|
+
</html>
|
@@ -0,0 +1,26 @@
|
|
1
|
+
Dear <%= @merchant.email %>,
|
2
|
+
|
3
|
+
🎉 FACILITATOR APPLICATION APPROVED!
|
4
|
+
|
5
|
+
Great news! Your facilitator application for "<%= @facilitator.name %>" has been approved.
|
6
|
+
|
7
|
+
<% if @total_limit %>
|
8
|
+
Approved Credit Limit: $<%= number_with_delimiter(@total_limit) %>
|
9
|
+
<% end %>
|
10
|
+
|
11
|
+
To complete your setup and start facilitating transactions, please submit your additional information by visiting:
|
12
|
+
|
13
|
+
<%= @additional_info_url %>
|
14
|
+
|
15
|
+
IMPORTANT NOTES:
|
16
|
+
• This link will expire in 30 days
|
17
|
+
• Complete your additional information to activate your facilitator account
|
18
|
+
• You'll receive a confirmation once your information is processed
|
19
|
+
|
20
|
+
If you have any questions, please don't hesitate to contact our support team.
|
21
|
+
|
22
|
+
Best regards,
|
23
|
+
The DSCF Credit Team
|
24
|
+
|
25
|
+
---
|
26
|
+
This is an automated email. Please do not reply to this message.
|
@@ -0,0 +1,39 @@
|
|
1
|
+
<!DOCTYPE html>
|
2
|
+
<html>
|
3
|
+
<head>
|
4
|
+
<meta charset="utf-8">
|
5
|
+
<style>
|
6
|
+
body { font-family: Arial, sans-serif; line-height: 1.6; color: #333; }
|
7
|
+
.container { max-width: 600px; margin: 0 auto; padding: 20px; }
|
8
|
+
.header { background-color: #d4edda; padding: 20px; border-radius: 5px; margin-bottom: 20px; }
|
9
|
+
.content { padding: 20px 0; }
|
10
|
+
.footer { margin-top: 30px; padding-top: 20px; border-top: 1px solid #eee; font-size: 12px; color: #666; }
|
11
|
+
</style>
|
12
|
+
</head>
|
13
|
+
<body>
|
14
|
+
<div class="container">
|
15
|
+
<div class="header">
|
16
|
+
<h1>💰 Facilitator Limit Updated</h1>
|
17
|
+
</div>
|
18
|
+
|
19
|
+
<div class="content">
|
20
|
+
<p>Dear <%= @merchant.email %>,</p>
|
21
|
+
|
22
|
+
<p>Your facilitator credit limit for <strong><%= @facilitator.name %></strong> has been updated.</p>
|
23
|
+
|
24
|
+
<p><strong>New Credit Limit:</strong> $<%= number_with_delimiter(@total_limit) %></p>
|
25
|
+
|
26
|
+
<p>This change is effective immediately. You can now facilitate transactions up to your new limit.</p>
|
27
|
+
|
28
|
+
<p>If you have any questions about this update, please contact our support team.</p>
|
29
|
+
|
30
|
+
<p>Best regards,<br>
|
31
|
+
The DSCF Credit Team</p>
|
32
|
+
</div>
|
33
|
+
|
34
|
+
<div class="footer">
|
35
|
+
<p>This is an automated email. Please do not reply to this message.</p>
|
36
|
+
</div>
|
37
|
+
</div>
|
38
|
+
</body>
|
39
|
+
</html>
|
@@ -0,0 +1,17 @@
|
|
1
|
+
Dear <%= @merchant.email %>,
|
2
|
+
|
3
|
+
💰 FACILITATOR LIMIT UPDATED
|
4
|
+
|
5
|
+
Your facilitator credit limit for "<%= @facilitator.name %>" has been updated.
|
6
|
+
|
7
|
+
New Credit Limit: $<%= number_with_delimiter(@total_limit) %>
|
8
|
+
|
9
|
+
This change is effective immediately. You can now facilitate transactions up to your new limit.
|
10
|
+
|
11
|
+
If you have any questions about this update, please contact our support team.
|
12
|
+
|
13
|
+
Best regards,
|
14
|
+
The DSCF Credit Team
|
15
|
+
|
16
|
+
---
|
17
|
+
This is an automated email. Please do not reply to this message.
|
@@ -0,0 +1,41 @@
|
|
1
|
+
<!DOCTYPE html>
|
2
|
+
<html>
|
3
|
+
<head>
|
4
|
+
<meta charset="utf-8">
|
5
|
+
<style>
|
6
|
+
body { font-family: Arial, sans-serif; line-height: 1.6; color: #333; }
|
7
|
+
.container { max-width: 600px; margin: 0 auto; padding: 20px; }
|
8
|
+
.header { background-color: #f8d7da; padding: 20px; border-radius: 5px; margin-bottom: 20px; }
|
9
|
+
.content { padding: 20px 0; }
|
10
|
+
.footer { margin-top: 30px; padding-top: 20px; border-top: 1px solid #eee; font-size: 12px; color: #666; }
|
11
|
+
</style>
|
12
|
+
</head>
|
13
|
+
<body>
|
14
|
+
<div class="container">
|
15
|
+
<div class="header">
|
16
|
+
<h1>📋 Facilitator Application Update</h1>
|
17
|
+
</div>
|
18
|
+
|
19
|
+
<div class="content">
|
20
|
+
<p>Dear <%= @merchant.email %>,</p>
|
21
|
+
|
22
|
+
<p>We regret to inform you that your facilitator application for <strong><%= @facilitator.name %></strong> has not been approved at this time.</p>
|
23
|
+
|
24
|
+
<% if @rejection_reason %>
|
25
|
+
<p><strong>Reason:</strong> <%= @rejection_reason %></p>
|
26
|
+
<% end %>
|
27
|
+
|
28
|
+
<p>You may resubmit your application after addressing any concerns or contact our support team for more information.</p>
|
29
|
+
|
30
|
+
<p>Thank you for your interest in becoming a facilitator with DSCF Credit.</p>
|
31
|
+
|
32
|
+
<p>Best regards,<br>
|
33
|
+
The DSCF Credit Team</p>
|
34
|
+
</div>
|
35
|
+
|
36
|
+
<div class="footer">
|
37
|
+
<p>This is an automated email. Please do not reply to this message.</p>
|
38
|
+
</div>
|
39
|
+
</div>
|
40
|
+
</body>
|
41
|
+
</html>
|
@@ -0,0 +1,19 @@
|
|
1
|
+
Dear <%= @merchant.email %>,
|
2
|
+
|
3
|
+
📋 FACILITATOR APPLICATION UPDATE
|
4
|
+
|
5
|
+
We regret to inform you that your facilitator application for "<%= @facilitator.name %>" has not been approved at this time.
|
6
|
+
|
7
|
+
<% if @rejection_reason %>
|
8
|
+
Reason: <%= @rejection_reason %>
|
9
|
+
<% end %>
|
10
|
+
|
11
|
+
You may resubmit your application after addressing any concerns or contact our support team for more information.
|
12
|
+
|
13
|
+
Thank you for your interest in becoming a facilitator with DSCF Credit.
|
14
|
+
|
15
|
+
Best regards,
|
16
|
+
The DSCF Credit Team
|
17
|
+
|
18
|
+
---
|
19
|
+
This is an automated email. Please do not reply to this message.
|