Browse Source

CLDC-2220 Update buyer pluralisation (#2272)

* Pluralise buyer in household characteristics/setup

* Pluralise buyer in sales information sections

* Pluralise buyer in savings

* Pluralise other buyers, update privacy notice test

* Pluralise buyer in validations and translations

* Route to pages when joint purchase is not answered

* Fix apostrophes

* Update translations

* More updates
pull/2289/head
kosiakkatrina 11 months ago committed by GitHub
parent
commit
ff55bed2b2
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
  1. 16
      app/models/form/sales/pages/buyer_interview.rb
  2. 20
      app/models/form/sales/pages/deposit_value_check.rb
  3. 2
      app/models/form/sales/pages/housing_benefits.rb
  4. 13
      app/models/form/sales/pages/living_before_purchase.rb
  5. 21
      app/models/form/sales/pages/old_persons_shared_ownership_value_check.rb
  6. 16
      app/models/form/sales/pages/privacy_notice.rb
  7. 18
      app/models/form/sales/pages/savings.rb
  8. 21
      app/models/form/sales/pages/savings_value_check.rb
  9. 10
      app/models/form/sales/questions/buyer_interview.rb
  10. 2
      app/models/form/sales/questions/housing_benefits.rb
  11. 6
      app/models/form/sales/questions/living_before_purchase.rb
  12. 2
      app/models/form/sales/questions/number_joint_buyers.rb
  13. 21
      app/models/form/sales/questions/privacy_notice.rb
  14. 6
      app/models/form/sales/questions/savings.rb
  15. 8
      app/models/form/sales/questions/savings_nk.rb
  16. 6
      app/models/form/sales/subsections/discounted_ownership_scheme.rb
  17. 12
      app/models/form/sales/subsections/household_characteristics.rb
  18. 9
      app/models/form/sales/subsections/income_benefits_and_savings.rb
  19. 3
      app/models/form/sales/subsections/outright_sale.rb
  20. 6
      app/models/form/sales/subsections/setup.rb
  21. 6
      app/models/form/sales/subsections/shared_ownership_scheme.rb
  22. 8
      app/models/validations/sales/financial_validations.rb
  23. 8
      app/models/validations/sales/property_validations.rb
  24. 1
      app/views/form/guidance/_privacy_notice_buyer_2024_joint_purchase.erb
  25. 1
      app/views/form/guidance/_privacy_notice_buyer_joint_purchase.erb
  26. 18
      config/locales/en.yml
  27. 4
      spec/models/form/sales/pages/buyer_interview_spec.rb
  28. 7
      spec/models/form/sales/pages/deposit_value_check_spec.rb
  29. 2
      spec/models/form/sales/pages/housing_benefits_spec.rb
  30. 12
      spec/models/form/sales/pages/living_before_purchase_spec.rb
  31. 29
      spec/models/form/sales/pages/old_persons_shared_ownership_value_check_spec.rb
  32. 20
      spec/models/form/sales/pages/privacy_notice_spec.rb
  33. 14
      spec/models/form/sales/pages/savings_spec.rb
  34. 20
      spec/models/form/sales/pages/savings_value_check_spec.rb
  35. 20
      spec/models/form/sales/questions/buyer_interview_spec.rb
  36. 2
      spec/models/form/sales/questions/living_before_purchase_spec.rb
  37. 2
      spec/models/form/sales/questions/number_joint_buyers_spec.rb
  38. 2
      spec/models/form/sales/questions/privacy_notice_spec.rb
  39. 2
      spec/models/form/sales/questions/savings_nk_spec.rb
  40. 2
      spec/models/form/sales/questions/savings_spec.rb
  41. 2
      spec/models/form/sales/subsections/discounted_ownership_scheme_spec.rb
  42. 10
      spec/models/form/sales/subsections/household_characteristics_spec.rb
  43. 6
      spec/models/form/sales/subsections/income_benefits_and_savings_spec.rb
  44. 3
      spec/models/form/sales/subsections/outright_sale_spec.rb
  45. 2
      spec/models/form/sales/subsections/setup_spec.rb
  46. 2
      spec/models/form/sales/subsections/shared_ownership_scheme_spec.rb
  47. 27
      spec/models/validations/sales/financial_validations_spec.rb
  48. 19
      spec/models/validations/sales/property_validations_spec.rb
  49. 9
      spec/models/validations/shared_validations_spec.rb
  50. 2
      spec/requests/lettings_logs_controller_spec.rb

16
app/models/form/sales/pages/buyer_interview.rb

@ -1,12 +1,20 @@
class Form::Sales::Pages::BuyerInterview < ::Form::Page
def initialize(id, hsh, subsection)
super
@id = "buyer_interview"
def initialize(id, hsh, subsection, joint_purchase:)
super(id, hsh, subsection)
@joint_purchase = joint_purchase
end
def questions
@questions ||= [
Form::Sales::Questions::BuyerInterview.new(nil, nil, self),
Form::Sales::Questions::BuyerInterview.new(nil, nil, self, joint_purchase: @joint_purchase),
]
end
def depends_on
if @joint_purchase
[{ "joint_purchase?" => true }]
else
[{ "not_joint_purchase?" => true }, { "jointpur" => nil }]
end
end
end

20
app/models/form/sales/pages/deposit_value_check.rb

@ -1,17 +1,12 @@
class Form::Sales::Pages::DepositValueCheck < ::Form::Page
def initialize(id, hsh, subsection)
super
@depends_on = [
{
"deposit_over_soft_max?" => true,
},
]
def initialize(id, hsh, subsection, joint_purchase:)
super(id, hsh, subsection)
@informative_text = {
"translation" => "soft_validations.deposit.hint_text",
"arguments" => [],
}
@title_text = {
"translation" => "soft_validations.deposit.title_text",
"translation" => "soft_validations.deposit.title_text.#{joint_purchase ? 'two' : 'one'}",
"arguments" => [
{
"key" => "field_formatted_as_currency",
@ -25,6 +20,7 @@ class Form::Sales::Pages::DepositValueCheck < ::Form::Page
},
],
}
@joint_purchase = joint_purchase
end
def questions
@ -36,4 +32,12 @@ class Form::Sales::Pages::DepositValueCheck < ::Form::Page
def interruption_screen_question_ids
%w[savings deposit]
end
def depends_on
if @joint_purchase
[{ "joint_purchase?" => true, "deposit_over_soft_max?" => true }]
else
[{ "not_joint_purchase?" => true, "deposit_over_soft_max?" => true }, { "jointpur" => nil, "deposit_over_soft_max?" => true }]
end
end
end

2
app/models/form/sales/pages/housing_benefits.rb

@ -14,7 +14,7 @@ class Form::Sales::Pages::HousingBenefits < ::Form::Page
if @joint_purchase
[{ "joint_purchase?" => true }]
else
[{ "not_joint_purchase?" => true }]
[{ "not_joint_purchase?" => true }, { "jointpur" => nil }]
end
end
end

13
app/models/form/sales/pages/living_before_purchase.rb

@ -1,7 +1,8 @@
class Form::Sales::Pages::LivingBeforePurchase < ::Form::Page
def initialize(id, hsh, subsection, ownershipsch:)
def initialize(id, hsh, subsection, ownershipsch:, joint_purchase:)
super(id, hsh, subsection)
@ownershipsch = ownershipsch
@joint_purchase = joint_purchase
end
def questions
@ -13,7 +14,15 @@ class Form::Sales::Pages::LivingBeforePurchase < ::Form::Page
def living_before_purchase
if form.start_date.year >= 2023
Form::Sales::Questions::LivingBeforePurchase.new(nil, nil, self, ownershipsch: @ownershipsch)
Form::Sales::Questions::LivingBeforePurchase.new(nil, nil, self, ownershipsch: @ownershipsch, joint_purchase: @joint_purchase)
end
end
def depends_on
if @joint_purchase
[{ "joint_purchase?" => true }]
else
[{ "not_joint_purchase?" => true }, { "jointpur" => nil }]
end
end
end

21
app/models/form/sales/pages/old_persons_shared_ownership_value_check.rb

@ -1,19 +1,15 @@
class Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck < ::Form::Page
def initialize(id, hsh, subsection)
super
@depends_on = [
{
"buyers_age_for_old_persons_shared_ownership_invalid?" => true,
},
]
def initialize(id, hsh, subsection, joint_purchase:)
super(id, hsh, subsection)
@title_text = {
"translation" => "soft_validations.old_persons_shared_ownership.title_text",
"translation" => "soft_validations.old_persons_shared_ownership.title_text.#{joint_purchase ? 'two' : 'one'}",
"arguments" => [],
}
@informative_text = {
"translation" => "soft_validations.old_persons_shared_ownership.hint_text",
"arguments" => [],
}
@joint_purchase = joint_purchase
end
def questions
@ -25,4 +21,13 @@ class Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck < ::Form::Page
def interruption_screen_question_ids
%w[type jointpur age1 age2]
end
def depends_on
if @joint_purchase
[{ "joint_purchase?" => true, "buyers_age_for_old_persons_shared_ownership_invalid?" => true }]
else
[{ "not_joint_purchase?" => true, "buyers_age_for_old_persons_shared_ownership_invalid?" => true },
{ "jointpur" => nil, "buyers_age_for_old_persons_shared_ownership_invalid?" => true }]
end
end
end

16
app/models/form/sales/pages/privacy_notice.rb

@ -1,13 +1,21 @@
class Form::Sales::Pages::PrivacyNotice < ::Form::Page
def initialize(id, hsh, subsection)
super
@id = "privacy_notice"
def initialize(id, hsh, subsection, joint_purchase:)
super(id, hsh, subsection)
@header = "Department for Levelling Up, Housing and Communities privacy notice"
@joint_purchase = joint_purchase
end
def questions
@questions ||= [
Form::Sales::Questions::PrivacyNotice.new(nil, nil, self),
Form::Sales::Questions::PrivacyNotice.new(nil, nil, self, joint_purchase: @joint_purchase),
]
end
def depends_on
if @joint_purchase
[{ "joint_purchase?" => true }]
else
[{ "not_joint_purchase?" => true }, { "jointpur" => nil }]
end
end
end

18
app/models/form/sales/pages/savings.rb

@ -1,13 +1,21 @@
class Form::Sales::Pages::Savings < ::Form::Page
def initialize(id, hsh, subsection)
super
@id = "savings"
def initialize(id, hsh, subsection, joint_purchase:)
super(id, hsh, subsection)
@joint_purchase = joint_purchase
end
def questions
@questions ||= [
Form::Sales::Questions::SavingsNk.new(nil, nil, self),
Form::Sales::Questions::Savings.new(nil, nil, self),
Form::Sales::Questions::SavingsNk.new(nil, nil, self, joint_purchase: @joint_purchase),
Form::Sales::Questions::Savings.new(nil, nil, self, joint_purchase: @joint_purchase),
]
end
def depends_on
if @joint_purchase
[{ "joint_purchase?" => true }]
else
[{ "not_joint_purchase?" => true }, { "jointpur" => nil }]
end
end
end

21
app/models/form/sales/pages/savings_value_check.rb

@ -1,13 +1,8 @@
class Form::Sales::Pages::SavingsValueCheck < ::Form::Page
def initialize(id, hsh, subsection)
super
@depends_on = [
{
"savings_over_soft_max?" => true,
},
]
def initialize(id, hsh, subsection, joint_purchase:)
super(id, hsh, subsection)
@title_text = {
"translation" => "soft_validations.savings.title_text",
"translation" => "soft_validations.savings.title_text.#{joint_purchase ? 'two' : 'one'}",
"arguments" => [
{
"key" => "field_formatted_as_currency",
@ -20,6 +15,7 @@ class Form::Sales::Pages::SavingsValueCheck < ::Form::Page
"translation" => "soft_validations.savings.hint_text",
"arguments" => [],
}
@joint_purchase = joint_purchase
end
def questions
@ -31,4 +27,13 @@ class Form::Sales::Pages::SavingsValueCheck < ::Form::Page
def interruption_screen_question_ids
%w[savings]
end
def depends_on
if @joint_purchase
[{ "joint_purchase?" => true, "savings_over_soft_max?" => true }]
else
[{ "not_joint_purchase?" => true, "savings_over_soft_max?" => true },
{ "jointpur" => nil, "savings_over_soft_max?" => true }]
end
end
end

10
app/models/form/sales/questions/buyer_interview.rb

@ -1,11 +1,11 @@
class Form::Sales::Questions::BuyerInterview < ::Form::Question
def initialize(id, hsh, page)
super
def initialize(id, hsh, page, joint_purchase:)
super(id, hsh, page)
@id = "noint"
@check_answer_label = "Buyer interviewed in person?"
@header = "Was the buyer interviewed for any of the answers you will provide on this log?"
@check_answer_label = "#{joint_purchase ? 'Buyers' : 'Buyer'} interviewed in person?"
@header = "#{joint_purchase ? 'Were the buyers' : 'Was the buyer'} interviewed for any of the answers you will provide on this log?"
@type = "radio"
@hint_text = "You should still try to answer all questions even if the buyer wasn't interviewed in person"
@hint_text = "You should still try to answer all questions even if the #{joint_purchase ? 'buyers weren’t' : 'buyer wasn’t'} interviewed in person"
@answer_options = ANSWER_OPTIONS
@question_number = 18
end

2
app/models/form/sales/questions/housing_benefits.rb

@ -2,7 +2,7 @@ class Form::Sales::Questions::HousingBenefits < ::Form::Question
def initialize(id, hsh, page, joint_purchase:)
super(id, hsh, page)
@id = "hb"
@check_answer_label = "Housing-related benefits buyer received before buying this property"
@check_answer_label = "Housing-related benefits #{joint_purchase ? 'buyers' : 'buyer'} received before buying this property"
@header = "#{joint_purchase ? 'Were the buyers' : 'Was the buyer'} receiving any of these housing-related benefits immediately before buying this property?"
@type = "radio"
@answer_options = ANSWER_OPTIONS

6
app/models/form/sales/questions/living_before_purchase.rb

@ -1,9 +1,9 @@
class Form::Sales::Questions::LivingBeforePurchase < ::Form::Question
def initialize(id, hsh, page, ownershipsch:)
def initialize(id, hsh, page, ownershipsch:, joint_purchase:)
super(id, hsh, page)
@id = "proplen_asked"
@check_answer_label = "Buyer lived in the property before purchasing"
@header = "Did the buyer live in the property before purchasing it?"
@check_answer_label = "#{joint_purchase ? 'Buyers' : 'Buyer'} lived in the property before purchasing"
@header = "Did the #{joint_purchase ? 'buyers' : 'buyer'} live in the property before purchasing it?"
@hint_text = nil
@type = "radio"
@answer_options = ANSWER_OPTIONS

2
app/models/form/sales/questions/number_joint_buyers.rb

@ -19,7 +19,7 @@ class Form::Sales::Questions::NumberJointBuyers < ::Form::Question
if form.start_year_after_2024?
nil
else
"You should still try to answer all questions even if the buyer wasn't interviewed in person"
"You should still try to answer all questions even if the buyers weren’t interviewed in person"
end
end
end

21
app/models/form/sales/questions/privacy_notice.rb

@ -1,21 +1,30 @@
class Form::Sales::Questions::PrivacyNotice < ::Form::Question
def initialize(id, hsh, page)
super
def initialize(id, hsh, page, joint_purchase:)
super(id, hsh, page)
@id = "privacynotice"
@check_answer_label = "Buyer has seen the privacy notice?"
@check_answer_label = "#{joint_purchase ? 'Buyers have' : 'Buyer has'} seen the privacy notice?"
@header = "Declaration"
@type = "checkbox"
@top_guidance_partial = form.start_year_after_2024? ? "privacy_notice_buyer_2024" : "privacy_notice_buyer"
@question_number = 19
@joint_purchase = joint_purchase
@top_guidance_partial = guidance
end
def answer_options
declaration_text = if form.start_year_after_2024?
"The buyer has seen or been given access to the DLUHC privacy notice"
"The #{@joint_purchase ? 'buyers have' : 'buyer has'} seen or been given access to the DLUHC privacy notice"
else
"The buyer has seen the DLUHC privacy notice"
"The #{@joint_purchase ? 'buyers have' : 'buyer has'} seen the DLUHC privacy notice"
end
{ "privacynotice" => { "value" => declaration_text } }.freeze
end
def guidance
if form.start_year_after_2024?
@joint_purchase ? "privacy_notice_buyer_2024_joint_purchase" : "privacy_notice_buyer_2024"
else
@joint_purchase ? "privacy_notice_buyer_joint_purchase" : "privacy_notice_buyer"
end
end
end

6
app/models/form/sales/questions/savings.rb

@ -1,8 +1,8 @@
class Form::Sales::Questions::Savings < ::Form::Question
def initialize(id, hsh, page)
super
def initialize(id, hsh, page, joint_purchase:)
super(id, hsh, page)
@id = "savings"
@check_answer_label = "Buyer’s total savings before any deposit paid"
@check_answer_label = "#{joint_purchase ? 'Buyers’' : 'Buyer’s'} total savings before any deposit paid"
@header = "Enter their total savings to the nearest £10"
@type = "numeric"
@width = 5

8
app/models/form/sales/questions/savings_nk.rb

@ -1,9 +1,9 @@
class Form::Sales::Questions::SavingsNk < ::Form::Question
def initialize(id, hsh, page)
super
def initialize(id, hsh, page, joint_purchase:)
super(id, hsh, page)
@id = "savingsnk"
@check_answer_label = "Buyer’s total savings known?"
@header = "Do you know how much the buyer had in savings before they paid any deposit for the property?"
@check_answer_label = "#{joint_purchase ? 'Buyers’' : 'Buyer’s'} total savings known?"
@header = "Do you know how much the #{joint_purchase ? 'buyers' : 'buyer'} had in savings before they paid any deposit for the property?"
@type = "radio"
@answer_options = ANSWER_OPTIONS
@conditional_for = {

6
app/models/form/sales/subsections/discounted_ownership_scheme.rb

@ -8,7 +8,8 @@ class Form::Sales::Subsections::DiscountedOwnershipScheme < ::Form::Subsection
def pages
@pages ||= [
Form::Sales::Pages::LivingBeforePurchase.new("living_before_purchase_discounted_ownership", nil, self, ownershipsch: 2),
Form::Sales::Pages::LivingBeforePurchase.new("living_before_purchase_discounted_ownership_joint_purchase", nil, self, ownershipsch: 2, joint_purchase: true),
Form::Sales::Pages::LivingBeforePurchase.new("living_before_purchase_discounted_ownership", nil, self, ownershipsch: 2, joint_purchase: false),
Form::Sales::Pages::AboutPriceRtb.new(nil, nil, self),
Form::Sales::Pages::ExtraBorrowingValueCheck.new("extra_borrowing_price_value_check", nil, self),
Form::Sales::Pages::PercentageDiscountValueCheck.new("percentage_discount_value_check", nil, self),
@ -33,7 +34,8 @@ class Form::Sales::Subsections::DiscountedOwnershipScheme < ::Form::Subsection
Form::Sales::Pages::ExtraBorrowingValueCheck.new("extra_borrowing_value_check", nil, self),
Form::Sales::Pages::AboutDepositWithoutDiscount.new("about_deposit_discounted_ownership", nil, self, ownershipsch: 2, optional: false),
Form::Sales::Pages::ExtraBorrowingValueCheck.new("extra_borrowing_deposit_value_check", nil, self),
Form::Sales::Pages::DepositValueCheck.new("discounted_ownership_deposit_value_check", nil, self),
Form::Sales::Pages::DepositValueCheck.new("discounted_ownership_deposit_joint_purchase_value_check", nil, self, joint_purchase: true),
Form::Sales::Pages::DepositValueCheck.new("discounted_ownership_deposit_value_check", nil, self, joint_purchase: false),
Form::Sales::Pages::DepositAndMortgageValueCheck.new("discounted_ownership_deposit_and_mortgage_value_check_after_deposit", nil, self),
Form::Sales::Pages::DiscountedSaleValueCheck.new("discounted_sale_deposit_value_check", nil, self),
Form::Sales::Pages::LeaseholdCharges.new("leasehold_charges_discounted_ownership", nil, self, ownershipsch: 2),

12
app/models/form/sales/subsections/household_characteristics.rb

@ -8,11 +8,14 @@ class Form::Sales::Subsections::HouseholdCharacteristics < ::Form::Subsection
def pages
@pages ||= [
(Form::Sales::Pages::BuyerInterview.new(nil, nil, self) unless form.start_year_after_2024?),
(Form::Sales::Pages::PrivacyNotice.new(nil, nil, self) unless form.start_year_after_2024?),
(Form::Sales::Pages::BuyerInterview.new("buyer_interview_joint_purchase", nil, self, joint_purchase: true) unless form.start_year_after_2024?),
(Form::Sales::Pages::BuyerInterview.new("buyer_interview", nil, self, joint_purchase: false) unless form.start_year_after_2024?),
(Form::Sales::Pages::PrivacyNotice.new("privacy_notice_joint_purchase", nil, self, joint_purchase: true) unless form.start_year_after_2024?),
(Form::Sales::Pages::PrivacyNotice.new("privacy_notice", nil, self, joint_purchase: false) unless form.start_year_after_2024?),
Form::Sales::Pages::Age1.new(nil, nil, self),
Form::Sales::Pages::RetirementValueCheck.new("age_1_retirement_value_check", nil, self, person_index: 1),
Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck.new("age_1_old_persons_shared_ownership_value_check", nil, self),
Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck.new("age_1_old_persons_shared_ownership_joint_purchase_value_check", nil, self, joint_purchase: true),
Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck.new("age_1_old_persons_shared_ownership_value_check", nil, self, joint_purchase: false),
Form::Sales::Pages::GenderIdentity1.new(nil, nil, self),
Form::Sales::Pages::RetirementValueCheck.new("gender_1_retirement_value_check", nil, self, person_index: 1),
Form::Sales::Pages::Buyer1EthnicGroup.new(nil, nil, self),
@ -30,7 +33,8 @@ class Form::Sales::Subsections::HouseholdCharacteristics < ::Form::Subsection
Form::Sales::Pages::Buyer2RelationshipToBuyer1.new(nil, nil, self),
Form::Sales::Pages::PersonStudentNotChildValueCheck.new("buyer_2_relationship_student_not_child_value_check", nil, self, person_index: 2),
Form::Sales::Pages::Age2.new(nil, nil, self),
Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck.new("age_2_old_persons_shared_ownership_value_check", nil, self),
Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck.new("age_2_old_persons_shared_ownership_joint_purchase_value_check", nil, self, joint_purchase: true),
Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck.new("age_2_old_persons_shared_ownership_value_check", nil, self, joint_purchase: false),
Form::Sales::Pages::RetirementValueCheck.new("age_2_buyer_retirement_value_check", nil, self, person_index: 2),
Form::Sales::Pages::PersonStudentNotChildValueCheck.new("buyer_2_age_student_not_child_value_check", nil, self, person_index: 2),
Form::Sales::Pages::GenderIdentity2.new(nil, nil, self),

9
app/models/form/sales/subsections/income_benefits_and_savings.rb

@ -24,9 +24,12 @@ class Form::Sales::Subsections::IncomeBenefitsAndSavings < ::Form::Subsection
Form::Sales::Pages::MortgageValueCheck.new("buyer_2_mortgage_value_check", nil, self, 2),
Form::Sales::Pages::HousingBenefits.new("housing_benefits_joint_purchase", nil, self, joint_purchase: true),
Form::Sales::Pages::HousingBenefits.new("housing_benefits_not_joint_purchase", nil, self, joint_purchase: false),
Form::Sales::Pages::Savings.new(nil, nil, self),
Form::Sales::Pages::SavingsValueCheck.new("savings_value_check", nil, self),
Form::Sales::Pages::DepositValueCheck.new("savings_deposit_value_check", nil, self),
Form::Sales::Pages::Savings.new("savings_joint_purchase", nil, self, joint_purchase: true),
Form::Sales::Pages::Savings.new("savings", nil, self, joint_purchase: false),
Form::Sales::Pages::SavingsValueCheck.new("savings_joint_purchase_value_check", nil, self, joint_purchase: true),
Form::Sales::Pages::SavingsValueCheck.new("savings_value_check", nil, self, joint_purchase: false),
Form::Sales::Pages::DepositValueCheck.new("savings_deposit_joint_purchase_value_check", nil, self, joint_purchase: true),
Form::Sales::Pages::DepositValueCheck.new("savings_deposit_value_check", nil, self, joint_purchase: false),
Form::Sales::Pages::PreviousOwnership.new("previous_ownership_joint_purchase", nil, self, joint_purchase: true),
Form::Sales::Pages::PreviousOwnership.new("previous_ownership_not_joint_purchase", nil, self, joint_purchase: false),
previous_shared_page,

3
app/models/form/sales/subsections/outright_sale.rb

@ -19,7 +19,8 @@ class Form::Sales::Subsections::OutrightSale < ::Form::Subsection
Form::Sales::Pages::MortgageLength.new("mortgage_length_outright_sale", nil, self, ownershipsch: 3),
Form::Sales::Pages::ExtraBorrowing.new("extra_borrowing_outright_sale", nil, self, ownershipsch: 3),
Form::Sales::Pages::AboutDepositWithoutDiscount.new("about_deposit_outright_sale", nil, self, ownershipsch: 3, optional: false),
Form::Sales::Pages::DepositValueCheck.new("outright_sale_deposit_value_check", nil, self),
Form::Sales::Pages::DepositValueCheck.new("outright_sale_deposit_joint_purchase_value_check", nil, self, joint_purchase: true),
Form::Sales::Pages::DepositValueCheck.new("outright_sale_deposit_value_check", nil, self, joint_purchase: false),
leasehold_charge_pages,
Form::Sales::Pages::MonthlyChargesValueCheck.new("monthly_charges_outright_sale_value_check", nil, self),
].flatten.compact

6
app/models/form/sales/subsections/setup.rb

@ -20,8 +20,10 @@ class Form::Sales::Subsections::Setup < ::Form::Subsection
Form::Sales::Pages::BuyerLive.new(nil, nil, self),
Form::Sales::Pages::JointPurchase.new(nil, nil, self),
Form::Sales::Pages::NumberJointBuyers.new(nil, nil, self),
(Form::Sales::Pages::BuyerInterview.new(nil, nil, self) if form.start_year_after_2024?),
(Form::Sales::Pages::PrivacyNotice.new(nil, nil, self) if form.start_year_after_2024?),
(Form::Sales::Pages::BuyerInterview.new("buyer_interview_joint_purchase", nil, self, joint_purchase: true) if form.start_year_after_2024?),
(Form::Sales::Pages::BuyerInterview.new("buyer_interview", nil, self, joint_purchase: false) if form.start_year_after_2024?),
(Form::Sales::Pages::PrivacyNotice.new("privacy_notice_joint_purchase", nil, self, joint_purchase: true) if form.start_year_after_2024?),
(Form::Sales::Pages::PrivacyNotice.new("privacy_notice", nil, self, joint_purchase: false) if form.start_year_after_2024?),
].flatten.compact
end
end

6
app/models/form/sales/subsections/shared_ownership_scheme.rb

@ -8,7 +8,8 @@ class Form::Sales::Subsections::SharedOwnershipScheme < ::Form::Subsection
def pages
@pages ||= [
Form::Sales::Pages::LivingBeforePurchase.new("living_before_purchase_shared_ownership", nil, self, ownershipsch: 1),
Form::Sales::Pages::LivingBeforePurchase.new("living_before_purchase_shared_ownership_joint_purchase", nil, self, ownershipsch: 1, joint_purchase: true),
Form::Sales::Pages::LivingBeforePurchase.new("living_before_purchase_shared_ownership", nil, self, ownershipsch: 1, joint_purchase: false),
Form::Sales::Pages::Staircase.new(nil, nil, self),
Form::Sales::Pages::AboutStaircase.new("about_staircasing_joint_purchase", nil, self, joint_purchase: true),
Form::Sales::Pages::AboutStaircase.new("about_staircasing_not_joint_purchase", nil, self, joint_purchase: false),
@ -41,7 +42,8 @@ class Form::Sales::Subsections::SharedOwnershipScheme < ::Form::Subsection
(Form::Sales::Pages::AboutDepositWithDiscount.new("about_deposit_with_discount_optional", nil, self, optional: true) if form.start_year_after_2024?),
Form::Sales::Pages::AboutDepositWithoutDiscount.new("about_deposit_shared_ownership", nil, self, ownershipsch: 1, optional: false),
(Form::Sales::Pages::AboutDepositWithoutDiscount.new("about_deposit_shared_ownership_optional", nil, self, ownershipsch: 1, optional: true) if form.start_year_after_2024?),
Form::Sales::Pages::DepositValueCheck.new("deposit_value_check", nil, self),
Form::Sales::Pages::DepositValueCheck.new("deposit_joint_purchase_value_check", nil, self, joint_purchase: true),
Form::Sales::Pages::DepositValueCheck.new("deposit_value_check", nil, self, joint_purchase: false),
Form::Sales::Pages::SharedOwnershipDepositValueCheck.new("shared_ownership_deposit_value_check", nil, self),
Form::Sales::Pages::MonthlyRent.new(nil, nil, self),
Form::Sales::Pages::LeaseholdCharges.new("leasehold_charges_shared_ownership", nil, self, ownershipsch: 1),

8
app/models/validations/sales/financial_validations.rb

@ -48,7 +48,7 @@ module Validations::Sales::FinancialValidations
return unless record.stairbought && record.stairowned
if record.stairbought > record.stairowned
record.errors.add :stairowned, I18n.t("validations.financial.staircasing.percentage_bought_must_be_greater_than_percentage_owned")
record.errors.add :stairowned, I18n.t("validations.financial.staircasing.percentage_bought_must_be_greater_than_percentage_owned", buyer_now_owns: record.joint_purchase? ? "buyers now own" : "buyer now owns")
end
end
@ -125,9 +125,9 @@ module Validations::Sales::FinancialValidations
if record.equity > record.stairowned - record.stairbought
formatted_equity = sprintf("%g", record.equity)
record.errors.add :equity, I18n.t("validations.financial.equity.over_stairowned_minus_stairbought", equity: formatted_equity, staircase_difference: record.stairowned - record.stairbought)
record.errors.add :stairowned, I18n.t("validations.financial.equity.over_stairowned_minus_stairbought", equity: formatted_equity, staircase_difference: record.stairowned - record.stairbought)
record.errors.add :stairbought, I18n.t("validations.financial.equity.over_stairowned_minus_stairbought", equity: formatted_equity, staircase_difference: record.stairowned - record.stairbought)
record.errors.add :equity, I18n.t("validations.financial.equity.over_stairowned_minus_stairbought", equity: formatted_equity, staircase_difference: record.stairowned - record.stairbought, buyer_owns: record.joint_purchase? ? "buyers own" : "buyer owns")
record.errors.add :stairowned, I18n.t("validations.financial.equity.over_stairowned_minus_stairbought", equity: formatted_equity, staircase_difference: record.stairowned - record.stairbought, buyer_owns: record.joint_purchase? ? "buyers own" : "buyer owns")
record.errors.add :stairbought, I18n.t("validations.financial.equity.over_stairowned_minus_stairbought", equity: formatted_equity, staircase_difference: record.stairowned - record.stairbought, buyer_owns: record.joint_purchase? ? "buyers own" : "buyer owns")
end
end

8
app/models/validations/sales/property_validations.rb

@ -4,10 +4,10 @@ module Validations::Sales::PropertyValidations
return unless record.ppostcode_full.present? && record.postcode_full.present?
if record.discounted_ownership_sale? && record.ppostcode_full != record.postcode_full
record.errors.add :postcode_full, I18n.t("validations.property.postcode.must_match_previous")
record.errors.add :ppostcode_full, I18n.t("validations.property.postcode.must_match_previous")
record.errors.add :ownershipsch, I18n.t("validations.property.postcode.must_match_previous")
record.errors.add :uprn, I18n.t("validations.property.postcode.must_match_previous")
record.errors.add :postcode_full, I18n.t("validations.property.postcode.must_match_previous", buyer_possessive: record.joint_purchase? ? "Buyers’" : "Buyer’s")
record.errors.add :ppostcode_full, I18n.t("validations.property.postcode.must_match_previous", buyer_possessive: record.joint_purchase? ? "Buyers’" : "Buyer’s")
record.errors.add :ownershipsch, I18n.t("validations.property.postcode.must_match_previous", buyer_possessive: record.joint_purchase? ? "Buyers’" : "Buyer’s")
record.errors.add :uprn, I18n.t("validations.property.postcode.must_match_previous", buyer_possessive: record.joint_purchase? ? "Buyers’" : "Buyer’s")
end
end

1
app/views/form/guidance/_privacy_notice_buyer_2024_joint_purchase.erb

@ -0,0 +1 @@
<p class="govuk-body">Make sure the buyers have seen or been given access to <%= govuk_link_to "the Department for Levelling Up, Housing & Communities (DLUHC) privacy notice", privacy_notice_path, target: :_blank %> before completing this log. This is a legal requirement under data protection legislation.</p>

1
app/views/form/guidance/_privacy_notice_buyer_joint_purchase.erb

@ -0,0 +1 @@
<p class="govuk-body">Make sure the buyers have seen <%= govuk_link_to "the Department for Levelling Up, Housing & Communities (DLUHC) privacy notice", privacy_notice_path, target: :_blank %> before completing this log.</p>

18
config/locales/en.yml

@ -350,7 +350,7 @@ en:
proptype:
bedsits_have_max_one_bedroom: "Answer cannot be 'Bedsit' if the property has 2 or more bedrooms"
postcode:
must_match_previous: "Buyer's last accommodation and discounted ownership postcodes must match"
must_match_previous: "%{buyer_possessive} last accommodation and discounted ownership postcodes must match"
financial:
tshortfall:
@ -428,7 +428,7 @@ en:
not_provided: "Enter how much rent and other charges the household pays %{period}"
cash_discount_invalid: "Cash discount must be £0 - £999,999"
staircasing:
percentage_bought_must_be_greater_than_percentage_owned: "Total percentage buyer now owns must be more than percentage bought in this transaction"
percentage_bought_must_be_greater_than_percentage_owned: "Total percentage %{buyer_now_owns} must be more than percentage bought in this transaction"
percentage_bought_must_be_at_least_threshold: "The minimum increase in equity while staircasing is %{threshold}%"
percentage_bought_equal_percentage_owned: "The percentage bought is %{stairbought}% and the percentage owned in total is %{stairowned}%. These figures cannot be the same."
monthly_leasehold_charges:
@ -436,7 +436,7 @@ en:
equity:
under_min: "The minimum initial equity stake for this type of shared ownership sale is %{min_equity}%"
over_max: "The maximum initial equity stake is %{max_equity}%"
over_stairowned_minus_stairbought: "The initial equity stake is %{equity}% and the percentage owned in total minus the percentage bought is %{staircase_difference}%. In a staircasing transaction, the equity stake purchased cannot be larger than the percentage the buyer owns minus the percentage bought."
over_stairowned_minus_stairbought: "The initial equity stake is %{equity}% and the percentage owned in total minus the percentage bought is %{staircase_difference}%. In a staircasing transaction, the equity stake purchased cannot be larger than the percentage the %{buyer_owns} minus the percentage bought."
mortgage: "Mortgage value cannot be £0 if a mortgage was used for the purchase of this property"
shared_ownership_deposit: "The %{mortgage_deposit_and_discount_error_fields} added together is %{mortgage_deposit_and_discount_total}. The value times the equity percentage is %{value_times_equity}. These figures should be the same"
@ -690,7 +690,9 @@ Make sure these answers are correct."
shared_ownership_deposit:
title_text: "You told us that the %{mortgage_deposit_and_discount_error_fields} add up to %{mortgage_deposit_and_discount_total}"
old_persons_shared_ownership:
title_text: "You told us the buyer is using the Older Persons Shared Ownership scheme."
title_text:
one: "You told us the buyer is using the Older Persons Shared Ownership scheme."
two: "You told us the buyers are using the Older Persons Shared Ownership scheme."
hint_text: "At least one buyer must be aged 65 years and over to use this scheme."
staircase_bought_seems_high:
title_text: "You told us that %{percentage}% was bought in this staircasing transaction."
@ -715,10 +717,14 @@ Make sure these answers are correct."
title_text: "You told us that the percentage discount is %{discount}."
hint_text: "This is higher than we would expect."
savings:
title_text: "You told us the buyer’s savings were %{savings}."
title_text:
one: "You told us the buyer’s savings were %{savings}."
two: "You told us the buyers’ savings were %{savings}."
hint_text: "This is higher than we would expect."
deposit:
title_text: "You told us the buyer’s deposit was %{deposit} and their savings were %{savings}."
title_text:
one: "You told us the buyer’s deposit was %{deposit} and their savings were %{savings}."
two: "You told us the buyers’ deposit was %{deposit} and their savings were %{savings}."
hint_text: "The deposit amount is higher than we would expect for the amount of savings they have."
grant:
title_text: "You told us that the grant amount is %{grant}"

4
spec/models/form/sales/pages/buyer_interview_spec.rb

@ -1,9 +1,9 @@
require "rails_helper"
RSpec.describe Form::Sales::Pages::BuyerInterview, type: :model do
subject(:page) { described_class.new(page_id, page_definition, subsection) }
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: false) }
let(:page_id) { nil }
let(:page_id) { "buyer_interview" }
let(:page_definition) { nil }
let(:subsection) { instance_double(Form::Subsection) }

7
spec/models/form/sales/pages/deposit_value_check_spec.rb

@ -1,7 +1,7 @@
require "rails_helper"
RSpec.describe Form::Sales::Pages::DepositValueCheck, type: :model do
subject(:page) { described_class.new(page_id, page_definition, subsection) }
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: false) }
let(:page_id) { "deposit_value_check" }
let(:page_definition) { nil }
@ -27,6 +27,11 @@ RSpec.describe Form::Sales::Pages::DepositValueCheck, type: :model do
expect(page.depends_on).to eq([
{
"deposit_over_soft_max?" => true,
"not_joint_purchase?" => true,
},
{
"deposit_over_soft_max?" => true,
"jointpur" => nil,
},
])
end

2
spec/models/form/sales/pages/housing_benefits_spec.rb

@ -30,7 +30,7 @@ RSpec.describe Form::Sales::Pages::HousingBenefits, type: :model do
context "when joint_purchase is false" do
it "has correct depends_on" do
expect(page.depends_on).to eq([{ "not_joint_purchase?" => true }])
expect(page.depends_on).to eq([{ "not_joint_purchase?" => true }, { "jointpur" => nil }])
end
end

12
spec/models/form/sales/pages/living_before_purchase_spec.rb

@ -1,7 +1,7 @@
require "rails_helper"
RSpec.describe Form::Sales::Pages::LivingBeforePurchase, type: :model do
subject(:page) { described_class.new(page_id, page_definition, subsection, ownershipsch: 1) }
subject(:page) { described_class.new(page_id, page_definition, subsection, ownershipsch: 1, joint_purchase: false) }
let(:page_id) { nil }
let(:page_definition) { nil }
@ -44,6 +44,14 @@ RSpec.describe Form::Sales::Pages::LivingBeforePurchase, type: :model do
end
it "has correct depends_on" do
expect(page.depends_on).to be_nil
expect(page.depends_on).to eq([{ "not_joint_purchase?" => true }, { "jointpur" => nil }])
end
context "with joint purchase" do
subject(:page) { described_class.new(page_id, page_definition, subsection, ownershipsch: 1, joint_purchase: true) }
it "has correct depends_on" do
expect(page.depends_on).to eq([{ "joint_purchase?" => true }])
end
end
end

29
spec/models/form/sales/pages/old_persons_shared_ownership_value_check_spec.rb

@ -1,7 +1,7 @@
require "rails_helper"
RSpec.describe Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck, type: :model do
subject(:page) { described_class.new(page_id, page_definition, subsection) }
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: false) }
let(:page_id) { "old_persons_shared_ownership_value_check" }
let(:page_definition) { nil }
@ -27,13 +27,18 @@ RSpec.describe Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck, type: :m
expect(page.depends_on).to eq([
{
"buyers_age_for_old_persons_shared_ownership_invalid?" => true,
"not_joint_purchase?" => true,
},
{
"buyers_age_for_old_persons_shared_ownership_invalid?" => true,
"jointpur" => nil,
},
])
end
it "has the correct title_text" do
expect(page.title_text).to eq({
"translation" => "soft_validations.old_persons_shared_ownership.title_text",
"translation" => "soft_validations.old_persons_shared_ownership.title_text.one",
"arguments" => [],
})
end
@ -45,4 +50,24 @@ RSpec.describe Form::Sales::Pages::OldPersonsSharedOwnershipValueCheck, type: :m
it "has the correct interruption_screen_question_ids" do
expect(page.interruption_screen_question_ids).to eq(%w[type jointpur age1 age2])
end
context "with joint purchase" do
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: true) }
it "has the correct title_text" do
expect(page.title_text).to eq({
"translation" => "soft_validations.old_persons_shared_ownership.title_text.two",
"arguments" => [],
})
end
it "has correct depends_on" do
expect(page.depends_on).to eq([
{
"buyers_age_for_old_persons_shared_ownership_invalid?" => true,
"joint_purchase?" => true,
},
])
end
end
end

20
spec/models/form/sales/pages/privacy_notice_spec.rb

@ -1,9 +1,9 @@
require "rails_helper"
RSpec.describe Form::Sales::Pages::PrivacyNotice, type: :model do
subject(:page) { described_class.new(page_id, page_definition, subsection) }
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: false) }
let(:page_id) { nil }
let(:page_id) { "privacy_notice" }
let(:page_definition) { nil }
let(:subsection) { instance_double(Form::Subsection) }
let(:form) { instance_double(Form) }
@ -34,6 +34,20 @@ RSpec.describe Form::Sales::Pages::PrivacyNotice, type: :model do
end
it "has correct depends_on" do
expect(page.depends_on).to be_nil
expect(page.depends_on).to eq([{ "not_joint_purchase?" => true }, { "jointpur" => nil }])
end
context "with joint purchase" do
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: true) }
let(:page_id) { "privacy_notice_joint_purchase" }
it "has correct depends_on" do
expect(page.depends_on).to eq([{ "joint_purchase?" => true }])
end
it "has the correct id" do
expect(page.id).to eq("privacy_notice_joint_purchase")
end
end
end

14
spec/models/form/sales/pages/savings_spec.rb

@ -1,9 +1,9 @@
require "rails_helper"
RSpec.describe Form::Sales::Pages::Savings, type: :model do
subject(:page) { described_class.new(page_id, page_definition, subsection) }
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: false) }
let(:page_id) { nil }
let(:page_id) { "savings" }
let(:page_definition) { nil }
let(:subsection) { instance_double(Form::Subsection) }
@ -28,6 +28,14 @@ RSpec.describe Form::Sales::Pages::Savings, type: :model do
end
it "has correct depends_on" do
expect(page.depends_on).to be_nil
expect(page.depends_on).to eq([{ "not_joint_purchase?" => true }, { "jointpur" => nil }])
end
context "with joint purchase" do
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: true) }
it "has correct depends_on" do
expect(page.depends_on).to eq([{ "joint_purchase?" => true }])
end
end
end

20
spec/models/form/sales/pages/savings_value_check_spec.rb

@ -1,7 +1,7 @@
require "rails_helper"
RSpec.describe Form::Sales::Pages::SavingsValueCheck, type: :model do
subject(:page) { described_class.new(page_id, page_definition, subsection) }
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: false) }
let(:page_id) { "savings_value_check" }
let(:page_definition) { nil }
@ -25,9 +25,10 @@ RSpec.describe Form::Sales::Pages::SavingsValueCheck, type: :model do
it "has correct depends_on" do
expect(page.depends_on).to eq([
{
"savings_over_soft_max?" => true,
},
{ "not_joint_purchase?" => true,
"savings_over_soft_max?" => true },
{ "jointpur" => nil,
"savings_over_soft_max?" => true },
])
end
@ -38,4 +39,15 @@ RSpec.describe Form::Sales::Pages::SavingsValueCheck, type: :model do
it "has the correct interruption_screen_question_ids" do
expect(page.interruption_screen_question_ids).to eq(%w[savings])
end
context "with joint purchase" do
subject(:page) { described_class.new(page_id, page_definition, subsection, joint_purchase: true) }
it "has correct depends_on" do
expect(page.depends_on).to eq([
{ "joint_purchase?" => true,
"savings_over_soft_max?" => true },
])
end
end
end

20
spec/models/form/sales/questions/buyer_interview_spec.rb

@ -1,7 +1,7 @@
require "rails_helper"
RSpec.describe Form::Sales::Questions::BuyerInterview, type: :model do
subject(:question) { described_class.new(question_id, question_definition, page) }
subject(:question) { described_class.new(question_id, question_definition, page, joint_purchase: false) }
let(:question_id) { nil }
let(:question_definition) { nil }
@ -32,7 +32,7 @@ RSpec.describe Form::Sales::Questions::BuyerInterview, type: :model do
end
it "has the correct hint" do
expect(question.hint_text).to eq("You should still try to answer all questions even if the buyer wasn't interviewed in person")
expect(question.hint_text).to eq("You should still try to answer all questions even if the buyer wasnt interviewed in person")
end
it "has the correct answer_options" do
@ -41,4 +41,20 @@ RSpec.describe Form::Sales::Questions::BuyerInterview, type: :model do
"1" => { "value" => "No" },
})
end
context "with joint purchase" do
subject(:question) { described_class.new(question_id, question_definition, page, joint_purchase: true) }
it "has the correct header" do
expect(question.header).to eq("Were the buyers interviewed for any of the answers you will provide on this log?")
end
it "has the correct hint_text" do
expect(question.hint_text).to eq("You should still try to answer all questions even if the buyers weren’t interviewed in person")
end
it "has the correct check_answer_label" do
expect(question.check_answer_label).to eq("Buyers interviewed in person?")
end
end
end

2
spec/models/form/sales/questions/living_before_purchase_spec.rb

@ -1,7 +1,7 @@
require "rails_helper"
RSpec.describe Form::Sales::Questions::LivingBeforePurchase, type: :model do
subject(:question) { described_class.new(question_id, question_definition, page, ownershipsch: 1) }
subject(:question) { described_class.new(question_id, question_definition, page, ownershipsch: 1, joint_purchase: false) }
let(:question_id) { nil }
let(:question_definition) { nil }

2
spec/models/form/sales/questions/number_joint_buyers_spec.rb

@ -38,7 +38,7 @@ RSpec.describe Form::Sales::Questions::NumberJointBuyers, type: :model do
end
it "has the correct hint_text" do
expect(question.hint_text).to eq("You should still try to answer all questions even if the buyer wasn't interviewed in person")
expect(question.hint_text).to eq("You should still try to answer all questions even if the buyers weren’t interviewed in person")
end
it "has the correct answer_options" do

2
spec/models/form/sales/questions/privacy_notice_spec.rb

@ -1,7 +1,7 @@
require "rails_helper"
RSpec.describe Form::Sales::Questions::PrivacyNotice, type: :model do
subject(:question) { described_class.new(question_id, question_definition, page) }
subject(:question) { described_class.new(question_id, question_definition, page, joint_purchase: false) }
let(:question_id) { nil }
let(:question_definition) { nil }

2
spec/models/form/sales/questions/savings_nk_spec.rb

@ -1,7 +1,7 @@
require "rails_helper"
RSpec.describe Form::Sales::Questions::SavingsNk, type: :model do
subject(:question) { described_class.new(question_id, question_definition, page) }
subject(:question) { described_class.new(question_id, question_definition, page, joint_purchase: false) }
let(:question_id) { nil }
let(:question_definition) { nil }

2
spec/models/form/sales/questions/savings_spec.rb

@ -1,7 +1,7 @@
require "rails_helper"
RSpec.describe Form::Sales::Questions::Savings, type: :model do
subject(:question) { described_class.new(question_id, question_definition, page) }
subject(:question) { described_class.new(question_id, question_definition, page, joint_purchase: false) }
let(:question_id) { nil }
let(:question_definition) { nil }

2
spec/models/form/sales/subsections/discounted_ownership_scheme_spec.rb

@ -14,6 +14,7 @@ RSpec.describe Form::Sales::Subsections::DiscountedOwnershipScheme, type: :model
it "has correct pages" do
expect(discounted_ownership_scheme.pages.map(&:id)).to eq(
%w[
living_before_purchase_discounted_ownership_joint_purchase
living_before_purchase_discounted_ownership
about_price_rtb
extra_borrowing_price_value_check
@ -39,6 +40,7 @@ RSpec.describe Form::Sales::Subsections::DiscountedOwnershipScheme, type: :model
extra_borrowing_value_check
about_deposit_discounted_ownership
extra_borrowing_deposit_value_check
discounted_ownership_deposit_joint_purchase_value_check
discounted_ownership_deposit_value_check
discounted_ownership_deposit_and_mortgage_value_check_after_deposit
discounted_sale_deposit_value_check

10
spec/models/form/sales/subsections/household_characteristics_spec.rb

@ -25,10 +25,13 @@ RSpec.describe Form::Sales::Subsections::HouseholdCharacteristics, type: :model
it "has correct pages" do
expect(household_characteristics.pages.map(&:id)).to eq(
%w[
buyer_interview_joint_purchase
buyer_interview
privacy_notice_joint_purchase
privacy_notice
buyer_1_age
age_1_retirement_value_check
age_1_old_persons_shared_ownership_joint_purchase_value_check
age_1_old_persons_shared_ownership_value_check
buyer_1_gender_identity
gender_1_retirement_value_check
@ -47,6 +50,7 @@ RSpec.describe Form::Sales::Subsections::HouseholdCharacteristics, type: :model
buyer_2_relationship_to_buyer_1
buyer_2_relationship_student_not_child_value_check
buyer_2_age
age_2_old_persons_shared_ownership_joint_purchase_value_check
age_2_old_persons_shared_ownership_value_check
age_2_buyer_retirement_value_check
buyer_2_age_student_not_child_value_check
@ -129,10 +133,13 @@ RSpec.describe Form::Sales::Subsections::HouseholdCharacteristics, type: :model
it "has correct pages" do
expect(household_characteristics.pages.map(&:id)).to eq(
%w[
buyer_interview_joint_purchase
buyer_interview
privacy_notice_joint_purchase
privacy_notice
buyer_1_age
age_1_retirement_value_check
age_1_old_persons_shared_ownership_joint_purchase_value_check
age_1_old_persons_shared_ownership_value_check
buyer_1_gender_identity
gender_1_retirement_value_check
@ -151,6 +158,7 @@ RSpec.describe Form::Sales::Subsections::HouseholdCharacteristics, type: :model
buyer_2_relationship_to_buyer_1
buyer_2_relationship_student_not_child_value_check
buyer_2_age
age_2_old_persons_shared_ownership_joint_purchase_value_check
age_2_old_persons_shared_ownership_value_check
age_2_buyer_retirement_value_check
buyer_2_age_student_not_child_value_check
@ -242,6 +250,7 @@ RSpec.describe Form::Sales::Subsections::HouseholdCharacteristics, type: :model
%w[
buyer_1_age
age_1_retirement_value_check
age_1_old_persons_shared_ownership_joint_purchase_value_check
age_1_old_persons_shared_ownership_value_check
buyer_1_gender_identity
gender_1_retirement_value_check
@ -260,6 +269,7 @@ RSpec.describe Form::Sales::Subsections::HouseholdCharacteristics, type: :model
buyer_2_relationship_to_buyer_1
buyer_2_relationship_student_not_child_value_check
buyer_2_age
age_2_old_persons_shared_ownership_joint_purchase_value_check
age_2_old_persons_shared_ownership_value_check
age_2_buyer_retirement_value_check
buyer_2_age_student_not_child_value_check

6
spec/models/form/sales/subsections/income_benefits_and_savings_spec.rb

@ -36,8 +36,11 @@ RSpec.describe Form::Sales::Subsections::IncomeBenefitsAndSavings, type: :model
buyer_2_mortgage_value_check
housing_benefits_joint_purchase
housing_benefits_not_joint_purchase
savings_joint_purchase
savings
savings_joint_purchase_value_check
savings_value_check
savings_deposit_joint_purchase_value_check
savings_deposit_value_check
previous_ownership_joint_purchase
previous_ownership_not_joint_purchase
@ -68,8 +71,11 @@ RSpec.describe Form::Sales::Subsections::IncomeBenefitsAndSavings, type: :model
buyer_2_mortgage_value_check
housing_benefits_joint_purchase
housing_benefits_not_joint_purchase
savings_joint_purchase
savings
savings_joint_purchase_value_check
savings_value_check
savings_deposit_joint_purchase_value_check
savings_deposit_value_check
previous_ownership_joint_purchase
previous_ownership_not_joint_purchase

3
spec/models/form/sales/subsections/outright_sale_spec.rb

@ -39,6 +39,7 @@ RSpec.describe Form::Sales::Subsections::OutrightSale, type: :model do
mortgage_length_outright_sale
extra_borrowing_outright_sale
about_deposit_outright_sale
outright_sale_deposit_joint_purchase_value_check
outright_sale_deposit_value_check
monthly_charges_outright_sale_value_check
],
@ -67,6 +68,7 @@ RSpec.describe Form::Sales::Subsections::OutrightSale, type: :model do
mortgage_length_outright_sale
extra_borrowing_outright_sale
about_deposit_outright_sale
outright_sale_deposit_joint_purchase_value_check
outright_sale_deposit_value_check
leasehold_charges_outright_sale
monthly_charges_outright_sale_value_check
@ -93,6 +95,7 @@ RSpec.describe Form::Sales::Subsections::OutrightSale, type: :model do
mortgage_length_outright_sale
extra_borrowing_outright_sale
about_deposit_outright_sale
outright_sale_deposit_joint_purchase_value_check
outright_sale_deposit_value_check
leasehold_charges_outright_sale
monthly_charges_outright_sale_value_check

2
spec/models/form/sales/subsections/setup_spec.rb

@ -67,7 +67,9 @@ RSpec.describe Form::Sales::Subsections::Setup, type: :model do
buyer_live
joint_purchase
number_joint_buyers
buyer_interview_joint_purchase
buyer_interview
privacy_notice_joint_purchase
privacy_notice
],
)

2
spec/models/form/sales/subsections/shared_ownership_scheme_spec.rb

@ -18,6 +18,7 @@ RSpec.describe Form::Sales::Subsections::SharedOwnershipScheme, type: :model do
it "has correct pages" do
expect(shared_ownership_scheme.pages.map(&:id)).to eq(
%w[
living_before_purchase_shared_ownership_joint_purchase
living_before_purchase_shared_ownership
staircasing
about_staircasing_joint_purchase
@ -49,6 +50,7 @@ RSpec.describe Form::Sales::Subsections::SharedOwnershipScheme, type: :model do
extra_borrowing_shared_ownership
about_deposit_with_discount
about_deposit_shared_ownership
deposit_joint_purchase_value_check
deposit_value_check
shared_ownership_deposit_value_check
monthly_rent

27
spec/models/validations/sales/financial_validations_spec.rb

@ -184,11 +184,20 @@ RSpec.describe Validations::Sales::FinancialValidations do
expect(record.errors).to be_empty
end
it "adds an error to stairowned and not stairbought if the percentage bought is more than the percentage owned" do
it "adds an error to stairowned and not stairbought if the percentage bought is more than the percentage owned for joint purchase" do
record.stairbought = 50
record.stairowned = 40
record.jointpur = 1
financial_validator.validate_percentage_bought_not_greater_than_percentage_owned(record)
expect(record.errors["stairowned"]).to include(match I18n.t("validations.financial.staircasing.percentage_bought_must_be_greater_than_percentage_owned"))
expect(record.errors["stairowned"]).to include("Total percentage buyers now own must be more than percentage bought in this transaction")
end
it "adds an error to stairowned and not stairbought if the percentage bought is more than the percentage owned for non joint purchase" do
record.stairbought = 50
record.stairowned = 40
record.jointpur = 2
financial_validator.validate_percentage_bought_not_greater_than_percentage_owned(record)
expect(record.errors["stairowned"]).to include("Total percentage buyer now owns must be more than percentage bought in this transaction")
end
end
@ -625,10 +634,22 @@ RSpec.describe Validations::Sales::FinancialValidations do
context "with a log in 24/25 collection year" do
let(:now) { Time.zone.local(2024, 4, 1) }
it "adds errors if equity is more than stairowned - stairbought" do
it "adds errors if equity is more than stairowned - stairbought for joint purchase" do
record.stairbought = 2
record.stairowned = 3
record.equity = 2
record.jointpur = 1
financial_validator.validate_equity_less_than_staircase_difference(record)
expect(record.errors["equity"]).to include("The initial equity stake is 2% and the percentage owned in total minus the percentage bought is 1%. In a staircasing transaction, the equity stake purchased cannot be larger than the percentage the buyers own minus the percentage bought.")
expect(record.errors["stairowned"]).to include("The initial equity stake is 2% and the percentage owned in total minus the percentage bought is 1%. In a staircasing transaction, the equity stake purchased cannot be larger than the percentage the buyers own minus the percentage bought.")
expect(record.errors["stairbought"]).to include("The initial equity stake is 2% and the percentage owned in total minus the percentage bought is 1%. In a staircasing transaction, the equity stake purchased cannot be larger than the percentage the buyers own minus the percentage bought.")
end
it "adds errors if equity is more than stairowned - stairbought for non joint purchase" do
record.stairbought = 2
record.stairowned = 3
record.equity = 2
record.jointpur = 2
financial_validator.validate_equity_less_than_staircase_difference(record)
expect(record.errors["equity"]).to include("The initial equity stake is 2% and the percentage owned in total minus the percentage bought is 1%. In a staircasing transaction, the equity stake purchased cannot be larger than the percentage the buyer owns minus the percentage bought.")
expect(record.errors["stairowned"]).to include("The initial equity stake is 2% and the percentage owned in total minus the percentage bought is 1%. In a staircasing transaction, the equity stake purchased cannot be larger than the percentage the buyer owns minus the percentage bought.")

19
spec/models/validations/sales/property_validations_spec.rb

@ -46,13 +46,24 @@ RSpec.describe Validations::Sales::PropertyValidations do
expect(record.errors["ownershipsch"]).to be_empty
end
it "when postcodes do not match an error is added" do
it "when postcodes do not match an error is added for joint purchase" do
record.postcode_full = "SW1A 1AA"
record.ppostcode_full = "SW1A 0AA"
record.jointpur = 1
property_validator.validate_postcodes_match_if_discounted_ownership(record)
expect(record.errors["postcode_full"]).to include(match I18n.t("validations.property.postcode.must_match_previous"))
expect(record.errors["ppostcode_full"]).to include(match I18n.t("validations.property.postcode.must_match_previous"))
expect(record.errors["ownershipsch"]).to include(match I18n.t("validations.property.postcode.must_match_previous"))
expect(record.errors["postcode_full"]).to include("Buyers’ last accommodation and discounted ownership postcodes must match")
expect(record.errors["ppostcode_full"]).to include("Buyers’ last accommodation and discounted ownership postcodes must match")
expect(record.errors["ownershipsch"]).to include("Buyers’ last accommodation and discounted ownership postcodes must match")
end
it "when postcodes do not match an error is added for non joint purchase" do
record.postcode_full = "SW1A 1AA"
record.ppostcode_full = "SW1A 0AA"
record.jointpur = 2
property_validator.validate_postcodes_match_if_discounted_ownership(record)
expect(record.errors["postcode_full"]).to include("Buyer’s last accommodation and discounted ownership postcodes must match")
expect(record.errors["ppostcode_full"]).to include("Buyer’s last accommodation and discounted ownership postcodes must match")
expect(record.errors["ownershipsch"]).to include("Buyer’s last accommodation and discounted ownership postcodes must match")
end
it "does not add error for 2024 log" do

9
spec/models/validations/shared_validations_spec.rb

@ -89,8 +89,9 @@ RSpec.describe Validations::SharedValidations do
it "adds the correct validation text when a question has a min but not a max" do
sales_log.savings = -10
sales_log.jointpur = 1
shared_validator.validate_numeric_min_max(sales_log)
expect(sales_log.errors["savings"]).to include(match I18n.t("validations.numeric.above_min", field: "Buyers total savings before any deposit paid", min: "£0"))
expect(sales_log.errors["savings"]).to include(match I18n.t("validations.numeric.above_min", field: "Buyers total savings before any deposit paid", min: "£0"))
end
context "when validating percent" do
@ -138,14 +139,16 @@ RSpec.describe Validations::SharedValidations do
context "when validating a question with a step of 10" do
it "adds an error if input is not a multiple of ten" do
sales_log.savings = 30_005
sales_log.jointpur = 1
shared_validator.validate_numeric_step(sales_log)
expect(sales_log.errors[:savings]).to include I18n.t("validations.numeric.nearest_ten", field: "Buyers total savings before any deposit paid")
expect(sales_log.errors[:savings]).to include I18n.t("validations.numeric.nearest_ten", field: "Buyers total savings before any deposit paid")
end
it "adds an error if the user attempts to input a number in exponent format" do
sales_log.savings = "3e5"
sales_log.jointpur = 1
shared_validator.validate_numeric_step(sales_log)
expect(sales_log.errors[:savings]).to include I18n.t("validations.numeric.nearest_ten", field: "Buyers total savings before any deposit paid")
expect(sales_log.errors[:savings]).to include I18n.t("validations.numeric.nearest_ten", field: "Buyers total savings before any deposit paid")
end
it "does not add an error if input is a multiple of ten" do

2
spec/requests/lettings_logs_controller_spec.rb

@ -1309,7 +1309,7 @@ RSpec.describe LettingsLogsController, type: :request do
expect(CGI.unescape_html(response.body)).to include("Not known")
end
it "shows `you haven't answered this question` if the question wasn't answered" do
it "shows `you haven't answered this question` if the question wasnt answered" do
get "/lettings-logs/#{id}/income-and-benefits/check-answers"
expect(CGI.unescape_html(response.body)).to include("You didn’t answer this question")
end

Loading…
Cancel
Save