instant_quote 1.7.33 → 1.7.34
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/Gemfile.lock +7 -5
- data/lib/instant_quote/adapter.rb +8 -0
- data/lib/instant_quote/adapter_finder.rb +4 -0
- data/lib/instant_quote/adapters/youlend.rb +45 -41
- data/lib/instant_quote/connection_translators/youlend.rb +14 -41
- data/lib/instant_quote/connection_translators/youlend_persons.rb +73 -0
- data/lib/instant_quote/decision_parsers/youlend.rb +106 -32
- data/lib/instant_quote/version.rb +1 -1
- data/lib/instant_quote.rb +4 -0
- metadata +4 -3
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 97b97adb2fb250be1f7b7a46b44cbb082500cb0dae53cb350e31123d506a1efe
|
|
4
|
+
data.tar.gz: 66ca99708c03bfbea6587abf097196998d366c1842026f43ce02b04705a779ae
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 9f94bf675fa6e919ece437296cad1684401ee435f9e2e54c1d86be65b94469f00d4e155187644c1e93ba75cc745a09554a9e988e45738d28d3b3ced25fa3b5a4
|
|
7
|
+
data.tar.gz: d095be67aa6e9b7f0d07d3bdebef1e89e95140b7435445b90287b8275814b071cceff5c657d8dd74bb97f7ac84c01cec156844fc8a6fb0a878daac1638ef279f
|
data/Gemfile.lock
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
PATH
|
|
2
2
|
remote: .
|
|
3
3
|
specs:
|
|
4
|
-
instant_quote (1.7.
|
|
4
|
+
instant_quote (1.7.34)
|
|
5
5
|
activesupport
|
|
6
6
|
capital_on_tap (~> 1.0.1)
|
|
7
7
|
iwoca (~> 1.1.0)
|
|
@@ -22,6 +22,7 @@ GEM
|
|
|
22
22
|
addressable (2.8.5)
|
|
23
23
|
public_suffix (>= 2.0.2, < 6.0)
|
|
24
24
|
ast (2.4.2)
|
|
25
|
+
base64 (0.1.1)
|
|
25
26
|
byebug (11.1.3)
|
|
26
27
|
capital_on_tap (1.0.1)
|
|
27
28
|
addressable
|
|
@@ -35,7 +36,8 @@ GEM
|
|
|
35
36
|
diff-lcs (1.5.0)
|
|
36
37
|
docile (1.4.0)
|
|
37
38
|
dotenv (2.8.1)
|
|
38
|
-
faraday (2.7.
|
|
39
|
+
faraday (2.7.11)
|
|
40
|
+
base64
|
|
39
41
|
faraday-net_http (>= 2.0, < 3.1)
|
|
40
42
|
ruby2_keywords (>= 0.0.4)
|
|
41
43
|
faraday-net_http (3.0.2)
|
|
@@ -51,7 +53,7 @@ GEM
|
|
|
51
53
|
json-schema (4.0.0)
|
|
52
54
|
addressable (>= 2.8)
|
|
53
55
|
method_source (1.0.0)
|
|
54
|
-
minitest (5.
|
|
56
|
+
minitest (5.20.0)
|
|
55
57
|
money (6.16.0)
|
|
56
58
|
i18n (>= 0.6.4, <= 2)
|
|
57
59
|
multi_json (1.15.0)
|
|
@@ -123,7 +125,7 @@ GEM
|
|
|
123
125
|
addressable (>= 2.8.0)
|
|
124
126
|
crack (>= 0.3.2)
|
|
125
127
|
hashdiff (>= 0.4.0, < 2.0.0)
|
|
126
|
-
youlend (1.
|
|
128
|
+
youlend (1.2.0)
|
|
127
129
|
addressable
|
|
128
130
|
faraday (~> 2.7)
|
|
129
131
|
rainbow
|
|
@@ -146,4 +148,4 @@ DEPENDENCIES
|
|
|
146
148
|
webmock
|
|
147
149
|
|
|
148
150
|
BUNDLED WITH
|
|
149
|
-
2.
|
|
151
|
+
2.3.10
|
|
@@ -40,6 +40,10 @@ module InstantQuote
|
|
|
40
40
|
new.get_approval(application_id, connection)
|
|
41
41
|
end
|
|
42
42
|
|
|
43
|
+
def self.accept_offer(application_id, connection, offer_id)
|
|
44
|
+
new.accept_offer(application_id, connection, offer_id)
|
|
45
|
+
end
|
|
46
|
+
|
|
43
47
|
def get_link(_connection)
|
|
44
48
|
raise NotImplementedError, "You must implement '#{self.class.name}#get_link'"
|
|
45
49
|
end
|
|
@@ -61,5 +65,9 @@ module InstantQuote
|
|
|
61
65
|
def get_approval(_application_id, _connection)
|
|
62
66
|
OpenStruct.new(success?: true)
|
|
63
67
|
end
|
|
68
|
+
|
|
69
|
+
def accept_offer(_application_id, _connection, _offer_id)
|
|
70
|
+
true
|
|
71
|
+
end
|
|
64
72
|
end
|
|
65
73
|
end
|
|
@@ -59,6 +59,10 @@ module InstantQuote
|
|
|
59
59
|
adapter.get_approval(connection.external_id, connection)
|
|
60
60
|
end
|
|
61
61
|
|
|
62
|
+
def accept_offer(offer_id)
|
|
63
|
+
adapter.accept_offer(connection.external_id, connection, offer_id)
|
|
64
|
+
end
|
|
65
|
+
|
|
62
66
|
def additional_fields
|
|
63
67
|
adapter.additional_fields
|
|
64
68
|
end
|
|
@@ -2,24 +2,12 @@
|
|
|
2
2
|
|
|
3
3
|
require 'youlend'
|
|
4
4
|
require 'instant_quote/decision_parsers/youlend'
|
|
5
|
+
require 'instant_quote/connection_translators/youlend_persons'
|
|
5
6
|
|
|
6
7
|
module InstantQuote
|
|
7
8
|
module Adapters
|
|
8
9
|
class Youlend < Adapter
|
|
9
10
|
additional_fields [
|
|
10
|
-
{
|
|
11
|
-
name: 'monthly_card_revenue',
|
|
12
|
-
label: 'Avg. monthly card revenue',
|
|
13
|
-
required: true,
|
|
14
|
-
type: 'money',
|
|
15
|
-
minimum: 1_000
|
|
16
|
-
},
|
|
17
|
-
{
|
|
18
|
-
name: 'monthly_revenue_from_invoices',
|
|
19
|
-
label: 'Avg. monthly revenue from invoices',
|
|
20
|
-
required: true,
|
|
21
|
-
type: 'money'
|
|
22
|
-
},
|
|
23
11
|
{
|
|
24
12
|
name: 'applicant_consent',
|
|
25
13
|
label: 'Yes, I give my consent for my data to be shared with YouLend',
|
|
@@ -28,48 +16,44 @@ module InstantQuote
|
|
|
28
16
|
}
|
|
29
17
|
]
|
|
30
18
|
|
|
31
|
-
# For Youlend we first need to
|
|
32
|
-
#
|
|
33
|
-
# while.
|
|
19
|
+
# For Youlend we first need to create a lead and then update lead
|
|
20
|
+
# since some of the fields are not available in create
|
|
34
21
|
def get_quote(params, connection)
|
|
35
|
-
|
|
22
|
+
data = create_lead(params)
|
|
36
23
|
|
|
37
|
-
|
|
38
|
-
|
|
24
|
+
update_lead(data[:leadId], params)
|
|
25
|
+
submit_persons(data[:leadId], connection)
|
|
39
26
|
|
|
40
|
-
|
|
41
|
-
end
|
|
27
|
+
connection.update(link: data[:signUpURL])
|
|
42
28
|
|
|
43
|
-
|
|
29
|
+
return data[:leadId]
|
|
44
30
|
end
|
|
45
31
|
|
|
46
|
-
def get_status(
|
|
32
|
+
def get_status(lead_id, connection)
|
|
33
|
+
details = ::Youlend::Lead.details(lead_id)
|
|
34
|
+
raise_error(details) unless details.success?
|
|
35
|
+
|
|
36
|
+
offers = ::Youlend::Lead.offers(lead_id) if details.body[:onboardingState] == 'offersProvided'
|
|
37
|
+
raise_error(offers) if offers && !offers.success?
|
|
38
|
+
|
|
39
|
+
decision = connection.approval_decision_info.merge(details: details.body)
|
|
40
|
+
decision.merge!(offers: offers&.body) if offers
|
|
41
|
+
|
|
42
|
+
connection.update(approval_decision_info: decision)
|
|
47
43
|
DecisionParsers::Youlend.new(connection.approval_decision_info)
|
|
48
44
|
end
|
|
49
45
|
|
|
46
|
+
def accept_offer(application_id, _connection, offer_id)
|
|
47
|
+
response = ::Youlend::Lead.accept_offer(application_id, offer_id)
|
|
48
|
+
|
|
49
|
+
response.success?
|
|
50
|
+
end
|
|
51
|
+
|
|
50
52
|
# Gets the URL for the given state key.
|
|
51
53
|
def get_link(connection)
|
|
52
54
|
connection.link
|
|
53
55
|
end
|
|
54
56
|
|
|
55
|
-
# Checks if the application is eligible for a loan. If it is we need to update the
|
|
56
|
-
# connection's approval_decision_info right away, since it's the only place where we get it.
|
|
57
|
-
def get_preapproval(params, connection)
|
|
58
|
-
# The preapproval endpoint doesn't work with all params, we need to remove some
|
|
59
|
-
params.delete(:companyName)
|
|
60
|
-
params.delete(:monthsTrading)
|
|
61
|
-
params.delete(:keyContactName)
|
|
62
|
-
params.delete(:registeredAddress)
|
|
63
|
-
params.delete(:thirdPartyLeadId)
|
|
64
|
-
params.delete(:contactPhoneNumber)
|
|
65
|
-
|
|
66
|
-
response = ::Youlend::Prequalification.verify(params)
|
|
67
|
-
|
|
68
|
-
connection.update(approval_decision_info: response.data) if response.success?
|
|
69
|
-
|
|
70
|
-
response
|
|
71
|
-
end
|
|
72
|
-
|
|
73
57
|
private
|
|
74
58
|
|
|
75
59
|
def raise_error(response)
|
|
@@ -79,6 +63,26 @@ module InstantQuote
|
|
|
79
63
|
error: response.errors.first || '[Youlend] API error'
|
|
80
64
|
)
|
|
81
65
|
end
|
|
66
|
+
|
|
67
|
+
def create_lead(params)
|
|
68
|
+
response = ::Youlend::Lead.create(params)
|
|
69
|
+
raise_error(response) unless response.success?
|
|
70
|
+
|
|
71
|
+
response.data
|
|
72
|
+
end
|
|
73
|
+
|
|
74
|
+
def update_lead(lead_id, params)
|
|
75
|
+
response = ::Youlend::Lead.update(lead_id, params)
|
|
76
|
+
raise_error(response) unless response.success?
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
def submit_persons(lead_id, connection)
|
|
80
|
+
people_translator = ConnectionTranslators::YoulendPersons.new(connection)
|
|
81
|
+
people_params = people_translator.translate
|
|
82
|
+
|
|
83
|
+
response = ::Youlend::SignificantPersons.create(lead_id, people_params)
|
|
84
|
+
raise_error(response) unless response.success?
|
|
85
|
+
end
|
|
82
86
|
end
|
|
83
87
|
end
|
|
84
88
|
end
|
|
@@ -5,58 +5,31 @@ module InstantQuote
|
|
|
5
5
|
CURRENCY = 'GBP'
|
|
6
6
|
|
|
7
7
|
class Youlend < ConnectionTranslator
|
|
8
|
-
# rubocop:disable Metrics/AbcSize
|
|
9
|
-
def translate
|
|
8
|
+
def translate # rubocop:disable Metrics/AbcSize
|
|
10
9
|
{
|
|
11
10
|
companyName: company.name,
|
|
12
11
|
companyType: company_type_translated,
|
|
12
|
+
companyNumber: company.company_number,
|
|
13
13
|
monthsTrading: company.total_months_in_business,
|
|
14
14
|
keyContactName: primary_user_name,
|
|
15
15
|
thirdPartyLeadId: application.code,
|
|
16
|
-
financialData: financial_data,
|
|
17
16
|
countryISOCode: 'GBR',
|
|
18
17
|
loanCurrencyISOCode: CURRENCY,
|
|
19
|
-
|
|
20
|
-
thirdPartyCustomerId: application&.primary_user&.id,
|
|
18
|
+
loanAmount: application.amount.to_f,
|
|
19
|
+
thirdPartyCustomerId: application&.primary_user&.id.to_s,
|
|
21
20
|
registeredAddress: company_address,
|
|
22
21
|
contactPhoneNumber: extra_info[:applicant_phone_number],
|
|
23
|
-
|
|
24
|
-
|
|
22
|
+
contactEmailAddress: application&.primary_user&.email,
|
|
23
|
+
# we need country and description on update
|
|
24
|
+
# but they are ignored in create
|
|
25
|
+
country: 'GBR',
|
|
26
|
+
description: application.description,
|
|
27
|
+
confirmedCreditSearch: true
|
|
25
28
|
}
|
|
26
29
|
end
|
|
27
|
-
# rubocop:enable Metrics/AbcSize
|
|
28
30
|
|
|
29
31
|
private
|
|
30
32
|
|
|
31
|
-
def financial_data
|
|
32
|
-
{
|
|
33
|
-
monthlyCardRevenue: extra_info[:monthly_card_revenue].to_i,
|
|
34
|
-
monthlyRevenueFromInvoices: extra_info[:monthly_revenue_from_invoices].to_i,
|
|
35
|
-
paymentData: payment_data
|
|
36
|
-
}
|
|
37
|
-
end
|
|
38
|
-
|
|
39
|
-
def payment_data
|
|
40
|
-
(1..12).to_a.map do |month|
|
|
41
|
-
formatted_month = format('%02<month>d', month: month)
|
|
42
|
-
|
|
43
|
-
{
|
|
44
|
-
paymentDate: "#{Date.today.year - 1}-#{formatted_month}-01",
|
|
45
|
-
amount: total_amount,
|
|
46
|
-
currencyISOCode: CURRENCY
|
|
47
|
-
}
|
|
48
|
-
end
|
|
49
|
-
end
|
|
50
|
-
|
|
51
|
-
def total_amount
|
|
52
|
-
@total_amount ||= begin
|
|
53
|
-
card = extra_info[:monthly_card_revenue].to_i || 0
|
|
54
|
-
invoices = extra_info[:monthly_revenue_from_invoices].to_i || 0
|
|
55
|
-
|
|
56
|
-
card + invoices
|
|
57
|
-
end
|
|
58
|
-
end
|
|
59
|
-
|
|
60
33
|
def company_address
|
|
61
34
|
address = company.address
|
|
62
35
|
|
|
@@ -81,13 +54,13 @@ module InstantQuote
|
|
|
81
54
|
def company_type_translated
|
|
82
55
|
case company.company_type.name
|
|
83
56
|
when /LTD/
|
|
84
|
-
'
|
|
57
|
+
'Ltd'
|
|
85
58
|
when /LLP/
|
|
86
|
-
'
|
|
59
|
+
'Llp'
|
|
87
60
|
when /PLC/
|
|
88
|
-
'
|
|
61
|
+
'Plc'
|
|
89
62
|
when 'Sole Trader'
|
|
90
|
-
'
|
|
63
|
+
'SoleTrader'
|
|
91
64
|
else
|
|
92
65
|
'other'
|
|
93
66
|
end
|
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module InstantQuote
|
|
4
|
+
module ConnectionTranslators
|
|
5
|
+
class YoulendPersons < ConnectionTranslator
|
|
6
|
+
def translate
|
|
7
|
+
people = application.borrower_organisation.company_people.map do |person|
|
|
8
|
+
translate_person(person)
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
{
|
|
12
|
+
significantPersons: people.select { |p| valid?(p) }
|
|
13
|
+
}
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
private
|
|
17
|
+
|
|
18
|
+
def valid?(person_hash)
|
|
19
|
+
person_hash.values_at(:address, :typeOfPerson, :dateOfBirth, :firstName, :surname)
|
|
20
|
+
.none?(&:nil?)
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def translate_person(person)
|
|
24
|
+
{
|
|
25
|
+
address: address(person),
|
|
26
|
+
dateOfBirth: date_of_birth(person),
|
|
27
|
+
firstName: person.first_name || person.name,
|
|
28
|
+
surname: person.last_name || person.name,
|
|
29
|
+
typeOfPerson: type_of_person(person),
|
|
30
|
+
emailAddress: application.primary_user.email,
|
|
31
|
+
mobilePhoneNumber: extra_info[:applicant_phone_number],
|
|
32
|
+
percentageOwned: person.shares_percent || 0,
|
|
33
|
+
nationality: person.nationality
|
|
34
|
+
}
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
def address(person)
|
|
38
|
+
address = person.address
|
|
39
|
+
return unless address
|
|
40
|
+
|
|
41
|
+
{
|
|
42
|
+
line1: address.line_1,
|
|
43
|
+
line2: address.line_2,
|
|
44
|
+
city: address.town,
|
|
45
|
+
region: address.town,
|
|
46
|
+
areaCode: address.postcode,
|
|
47
|
+
country: address.country
|
|
48
|
+
}
|
|
49
|
+
end
|
|
50
|
+
|
|
51
|
+
def type_of_person(person)
|
|
52
|
+
if person.director? && person.shareholder?
|
|
53
|
+
'DirectorAndBeneficialOwner'
|
|
54
|
+
elsif person.director?
|
|
55
|
+
'Director'
|
|
56
|
+
elsif person.shareholder?
|
|
57
|
+
'BeneficialOwner'
|
|
58
|
+
end
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
def date_of_birth(person)
|
|
62
|
+
dob = person.birthdate || application.primary_user.birthdate
|
|
63
|
+
return unless dob
|
|
64
|
+
|
|
65
|
+
{
|
|
66
|
+
year: dob.year,
|
|
67
|
+
month: dob.month,
|
|
68
|
+
day: dob.day
|
|
69
|
+
}
|
|
70
|
+
end
|
|
71
|
+
end
|
|
72
|
+
end
|
|
73
|
+
end
|
|
@@ -6,71 +6,145 @@ module InstantQuote
|
|
|
6
6
|
module DecisionParsers
|
|
7
7
|
# Example response:
|
|
8
8
|
#
|
|
9
|
+
# Details response merged with optional offers
|
|
9
10
|
# {
|
|
10
|
-
#
|
|
11
|
-
#
|
|
12
|
-
#
|
|
13
|
-
#
|
|
14
|
-
#
|
|
15
|
-
#
|
|
16
|
-
#
|
|
17
|
-
#
|
|
18
|
-
#
|
|
19
|
-
#
|
|
11
|
+
# "details": {
|
|
12
|
+
# "leadSourceLendingPartnerId": "2487faad-24c3-40ed-8e63-f4551555116a",
|
|
13
|
+
# "onboardingState": "offersProvided",
|
|
14
|
+
# "onboardingStateReason": "",
|
|
15
|
+
# "organisationDetailsStepComplete": true,
|
|
16
|
+
# "paymentDataStepComplete": true,
|
|
17
|
+
# "offerStepComplete": false,
|
|
18
|
+
# "kycDocumentsStepComplete": true,
|
|
19
|
+
# "companyName": "SATURDAY LTD",
|
|
20
|
+
# "leadType": "Api",
|
|
21
|
+
# "signingDetails": {
|
|
22
|
+
# "eligibleForInstantSigning": false,
|
|
23
|
+
# "instantSigningDetails": null
|
|
24
|
+
# }
|
|
25
|
+
# },
|
|
26
|
+
# "offers": {
|
|
27
|
+
# "leadId": "5c35a9f4-436e-47b9-a31c-b55f5881f8be",
|
|
28
|
+
# "previousAcceptedOffer": null,
|
|
29
|
+
# "providedOffers": [
|
|
30
|
+
# {
|
|
31
|
+
# "offerId": "12cfda2b-cfb6-4d79-bd16-2979ed6a069a",
|
|
32
|
+
# "youWillGet": 6000,
|
|
33
|
+
# "youWillRepay": 7020,
|
|
34
|
+
# "currencyISOCode": "GBP",
|
|
35
|
+
# "sweep": 20,
|
|
36
|
+
# "minimumWeeklyRepayment": 150.28,
|
|
37
|
+
# "daysUntilRepayment": 218,
|
|
38
|
+
# "maturityDate": "2024-06-26T16:42:15.038Z"
|
|
39
|
+
# },
|
|
40
|
+
# {
|
|
41
|
+
# "offerId": "2d93cb8b-7e3b-4c87-87cf-40e2f7e226e3",
|
|
42
|
+
# "youWillGet": 6500,
|
|
43
|
+
# "youWillRepay": 7735,
|
|
44
|
+
# "currencyISOCode": "GBP",
|
|
45
|
+
# "sweep": 20,
|
|
46
|
+
# "minimumWeeklyRepayment": 150.4,
|
|
47
|
+
# "daysUntilRepayment": 240,
|
|
48
|
+
# "maturityDate": "2024-07-29T16:42:15.038Z"
|
|
49
|
+
# },
|
|
50
|
+
# {
|
|
51
|
+
# "offerId": "f2ef06ef-0c29-418c-ad93-d7abdee5994e",
|
|
52
|
+
# "youWillGet": 7000,
|
|
53
|
+
# "youWillRepay": 8470,
|
|
54
|
+
# "currencyISOCode": "GBP",
|
|
55
|
+
# "sweep": 20,
|
|
56
|
+
# "minimumWeeklyRepayment": 150.1,
|
|
57
|
+
# "daysUntilRepayment": 263,
|
|
58
|
+
# "maturityDate": "2024-09-02T16:42:15.038Z"
|
|
59
|
+
# }
|
|
60
|
+
# ],
|
|
61
|
+
# "acceptedOffer": null,
|
|
62
|
+
# "unsignedLoanDocument": null,
|
|
63
|
+
# "unsignedLoanDocumentDownloaded": false,
|
|
64
|
+
# "documentSigningId": "00000000-0000-0000-0000-000000000000",
|
|
65
|
+
# "sortCode": null,
|
|
66
|
+
# "accountNumber": null,
|
|
67
|
+
# "swift": null,
|
|
68
|
+
# "iban": null,
|
|
69
|
+
# "bankName": null,
|
|
70
|
+
# "confirmedCompanyAccount": false,
|
|
71
|
+
# "minFundingAmount": 0,
|
|
72
|
+
# "maxFundingAmount": 0
|
|
73
|
+
# }
|
|
20
74
|
# }
|
|
75
|
+
#
|
|
21
76
|
class Youlend < DecisionParser
|
|
77
|
+
APPROVED_STATES = %w[offersProvided offerAccepted contractgenerated contractsigned]
|
|
78
|
+
|
|
22
79
|
def approved?
|
|
23
|
-
|
|
80
|
+
APPROVED_STATES.include?(status) && loan_offer.present?
|
|
24
81
|
end
|
|
25
82
|
|
|
26
83
|
def declined?
|
|
27
|
-
!approved?
|
|
84
|
+
!(approved? || incomplete? || submitted? || pending?)
|
|
85
|
+
end
|
|
86
|
+
|
|
87
|
+
def pending?
|
|
88
|
+
data.nil? || data.empty?
|
|
89
|
+
end
|
|
90
|
+
|
|
91
|
+
def submitted?
|
|
92
|
+
status == 'stage1submitted'
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
def incomplete?
|
|
96
|
+
status == 'stage1incomplete'
|
|
28
97
|
end
|
|
29
98
|
|
|
30
99
|
def sweep
|
|
31
100
|
return '-' unless approved?
|
|
32
101
|
|
|
33
|
-
|
|
102
|
+
loan_offer[:sweep]
|
|
34
103
|
end
|
|
35
104
|
|
|
36
105
|
def status
|
|
37
106
|
approved? ? 'approved' : 'declined'
|
|
38
107
|
end
|
|
39
108
|
|
|
40
|
-
def fee
|
|
41
|
-
fee = funded_option[:fee].to_f || 0
|
|
42
|
-
|
|
43
|
-
Money.new(fee * 100).format
|
|
44
|
-
end
|
|
45
|
-
|
|
46
109
|
def loan_amount
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
Money.new(amount * 100).format
|
|
110
|
+
Money.new(raw_loan_amount * 100).format
|
|
50
111
|
end
|
|
51
112
|
|
|
52
113
|
def funded_amount
|
|
53
|
-
|
|
114
|
+
Money.new(raw_funded_amount * 100).format
|
|
115
|
+
end
|
|
116
|
+
|
|
117
|
+
def fee
|
|
118
|
+
Money.new(raw_fee_amount * 100).format
|
|
119
|
+
end
|
|
54
120
|
|
|
55
|
-
|
|
121
|
+
def offer_id
|
|
122
|
+
loan_offer[:offerId]
|
|
56
123
|
end
|
|
57
124
|
|
|
58
125
|
alias amount funded_amount
|
|
59
126
|
|
|
60
127
|
private
|
|
61
128
|
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
end
|
|
129
|
+
# Ideally we want to give the borrower the highest amount on offer.
|
|
130
|
+
def loan_offer
|
|
131
|
+
@loan_offer ||= (data.dig(:offers, :providedOffers) || []).max_by { |offer| offer[:youWillGet].to_f }
|
|
66
132
|
end
|
|
67
133
|
|
|
68
|
-
def
|
|
69
|
-
|
|
134
|
+
def raw_fee_amount
|
|
135
|
+
raw_loan_amount - raw_funded_amount
|
|
136
|
+
end
|
|
70
137
|
|
|
71
|
-
|
|
138
|
+
def raw_funded_amount
|
|
139
|
+
loan_offer&.dig(:youWillGet)&.to_f || 0
|
|
140
|
+
end
|
|
72
141
|
|
|
73
|
-
|
|
142
|
+
def raw_loan_amount
|
|
143
|
+
loan_offer&.dig(:youWillRepay)&.to_f || 0
|
|
144
|
+
end
|
|
145
|
+
|
|
146
|
+
def status
|
|
147
|
+
data.dig(:details, :onboardingState)
|
|
74
148
|
end
|
|
75
149
|
end
|
|
76
150
|
end
|
data/lib/instant_quote.rb
CHANGED
metadata
CHANGED
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: instant_quote
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 1.7.
|
|
4
|
+
version: 1.7.34
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- rikas
|
|
8
8
|
autorequire:
|
|
9
9
|
bindir: exe
|
|
10
10
|
cert_chain: []
|
|
11
|
-
date: 2023-09-
|
|
11
|
+
date: 2023-09-15 00:00:00.000000000 Z
|
|
12
12
|
dependencies:
|
|
13
13
|
- !ruby/object:Gem::Dependency
|
|
14
14
|
name: activesupport
|
|
@@ -150,6 +150,7 @@ files:
|
|
|
150
150
|
- lib/instant_quote/connection_translators/iwoca_revenue_based_loans.rb
|
|
151
151
|
- lib/instant_quote/connection_translators/optimum.rb
|
|
152
152
|
- lib/instant_quote/connection_translators/youlend.rb
|
|
153
|
+
- lib/instant_quote/connection_translators/youlend_persons.rb
|
|
153
154
|
- lib/instant_quote/decision_parser.rb
|
|
154
155
|
- lib/instant_quote/decision_parsers/capital_on_tap.rb
|
|
155
156
|
- lib/instant_quote/decision_parsers/fake.rb
|
|
@@ -183,7 +184,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
183
184
|
- !ruby/object:Gem::Version
|
|
184
185
|
version: '0'
|
|
185
186
|
requirements: []
|
|
186
|
-
rubygems_version: 3.
|
|
187
|
+
rubygems_version: 3.0.8
|
|
187
188
|
signing_key:
|
|
188
189
|
specification_version: 4
|
|
189
190
|
summary: Instant quote providers gem.
|