If your organisation’s schemes were migrated from old CORE, they may have new names and codes. Search by postcode to find your scheme.
"
scheme_changes_link_text: "Read more about how schemes have changed"
view_schemes_link_text: "View your organisation’s schemes"
-
+
privacy_notice_tenant:
content: "Make sure the lead tenant has seen or been given access to %{privacy_notice_link} before completing this log. This is a legal requirement under data protection legislation."
privacy_notice_link_text: "the Ministry of Housing, Communities and Local Government (MHCLG) privacy notice"
@@ -60,11 +60,4 @@ en:
Some properties may not be available yet e.g. new builds; you might need to enter them manually instead
-
For UPRN (Unique Property Reference Number), please enter the full value exactly
-
"
+ "
\ No newline at end of file
diff --git a/config/locales/forms/2024/lettings/property_information.en.yml b/config/locales/forms/2024/lettings/property_information.en.yml
index 016c78958..9e7326040 100644
--- a/config/locales/forms/2024/lettings/property_information.en.yml
+++ b/config/locales/forms/2024/lettings/property_information.en.yml
@@ -50,13 +50,6 @@ en:
hint_text: ""
question_text: "Select the correct address"
- address_search:
- page_header: "What is the property's address?"
- check_answer_label: "Address"
- check_answer_prompt: "Enter address or UPRN"
- hint_text: "For example, '1 Victoria Road' or '10010457355'"
- question_text: "Enter address or UPRN"
-
address:
page_header: "What is the property's address?"
address_line1:
diff --git a/config/locales/forms/2024/sales/guidance.en.yml b/config/locales/forms/2024/sales/guidance.en.yml
index b57595c66..801c43a5c 100644
--- a/config/locales/forms/2024/sales/guidance.en.yml
+++ b/config/locales/forms/2024/sales/guidance.en.yml
@@ -44,10 +44,3 @@ en:
privacy_notice_buyer:
content: "Make sure the buyer has seen or been given access to %{privacy_notice_link} before completing this log. This is a legal requirement under data protection legislation."
privacy_notice_link_text: "the Ministry of Housing, Communities and Local Government (MHCLG) privacy notice"
-
- address_search:
- title: "Can’t find the address you’re looking for?"
- content: "
-
Some properties may not be available yet e.g. new builds; you might need to enter them manually instead
-
For UPRN (Unique Property Reference Number), please enter the full value exactly
-
"
diff --git a/config/locales/forms/2024/sales/property_information.en.yml b/config/locales/forms/2024/sales/property_information.en.yml
index 518654211..b40e40267 100644
--- a/config/locales/forms/2024/sales/property_information.en.yml
+++ b/config/locales/forms/2024/sales/property_information.en.yml
@@ -43,13 +43,6 @@ en:
hint_text: ""
question_text: "Select the correct address"
- address_search:
- page_header: "What is the property's address?"
- check_answer_label: "Address"
- check_answer_prompt: "Enter address or UPRN"
- hint_text: "For example, '1 Victoria Road' or '10010457355'"
- question_text: "Enter address or UPRN"
-
address:
page_header: "What is the property's address?"
address_line1:
diff --git a/config/locales/forms/2025/lettings/guidance.en.yml b/config/locales/forms/2025/lettings/guidance.en.yml
index cb51fbf9d..340eb11d5 100644
--- a/config/locales/forms/2025/lettings/guidance.en.yml
+++ b/config/locales/forms/2025/lettings/guidance.en.yml
@@ -61,10 +61,3 @@ en:
Some properties may not be available yet e.g. new builds; you might need to enter them manually instead
-
For UPRN (Unique Property Reference Number), please enter the full value exactly
-
"
diff --git a/config/locales/forms/2025/lettings/property_information.en.yml b/config/locales/forms/2025/lettings/property_information.en.yml
index 41cf2d3aa..22a0d12db 100644
--- a/config/locales/forms/2025/lettings/property_information.en.yml
+++ b/config/locales/forms/2025/lettings/property_information.en.yml
@@ -10,12 +10,45 @@ en:
hint_text: ""
question_text: "Is this the first time the property has been let as social housing?"
- address_search:
- page_header: "What is the property's address?"
- check_answer_label: "Address"
- check_answer_prompt: "Enter address or UPRN"
- hint_text: "For example, '1 Victoria Road' or '10010457355'"
- question_text: "Enter address or UPRN"
+ uprn:
+ page_header: ""
+ uprn_known:
+ check_answer_label: "UPRN known"
+ check_answer_prompt: "Enter UPRN if known"
+ hint_text: "The Unique Property Reference Number (UPRN) is a unique number system created by Ordnance Survey and used by housing providers and various industries across the UK. An example UPRN is 10010457355.
The UPRN may not be the same as the property reference assigned by your organisation.
If you don’t know the UPRN you can enter the address of the property instead on the next screen."
+ question_text: "Do you know the property's UPRN?"
+ uprn:
+ check_answer_label: "UPRN"
+ check_answer_prompt: ""
+ hint_text: ""
+ question_text: "What is the property's UPRN?"
+
+ uprn_confirmed:
+ page_header: "We found an address that might be this property"
+ check_answer_label: "Is this the right address?"
+ check_answer_prompt: "Tell us if this is the right address"
+ hint_text: ""
+ question_text: "Is this the property address?"
+
+ address_matcher:
+ page_header: "Find an address"
+ address_line1_input:
+ check_answer_label: "Find address"
+ check_answer_prompt: "Try find address"
+ hint_text: ""
+ question_text: "Address line 1"
+ postcode_full_input:
+ check_answer_label: ""
+ check_answer_prompt: ""
+ hint_text: ""
+ question_text: "Postcode"
+
+ uprn_selection:
+ page_header: "We found an address that might be this property"
+ check_answer_label: "Select correct address"
+ check_answer_prompt: "Select correct address"
+ hint_text: ""
+ question_text: "Select the correct address"
address:
page_header: "What is the property's address?"
diff --git a/config/locales/forms/2025/sales/guidance.en.yml b/config/locales/forms/2025/sales/guidance.en.yml
index cfb9b0615..4ed6796b3 100644
--- a/config/locales/forms/2025/sales/guidance.en.yml
+++ b/config/locales/forms/2025/sales/guidance.en.yml
@@ -44,10 +44,3 @@ en:
privacy_notice_buyer:
content: "Make sure the buyer has seen or been given access to %{privacy_notice_link} before completing this log. This is a legal requirement under data protection legislation."
privacy_notice_link_text: "the Ministry of Housing, Communities and Local Government (MHCLG) privacy notice"
-
- address_search:
- title: "Can’t find the address you’re looking for?"
- content: "
-
Some properties may not be available yet e.g. new builds; you might need to enter them manually instead
-
For UPRN (Unique Property Reference Number), please enter the full value exactly
-
"
diff --git a/config/locales/forms/2025/sales/property_information.en.yml b/config/locales/forms/2025/sales/property_information.en.yml
index e91089bc5..332219a6b 100644
--- a/config/locales/forms/2025/sales/property_information.en.yml
+++ b/config/locales/forms/2025/sales/property_information.en.yml
@@ -3,12 +3,45 @@ en:
2025:
sales:
property_information:
- address_search:
- page_header: "What is the property's address?"
- check_answer_label: "Address"
- check_answer_prompt: "Enter address or UPRN"
- hint_text: "For example, '1 Victoria Road' or '10010457355'"
- question_text: "Enter address or UPRN"
+ uprn:
+ page_header: ""
+ uprn_known:
+ check_answer_label: "UPRN known"
+ check_answer_prompt: "Enter UPRN if known"
+ hint_text: "The Unique Property Reference Number (UPRN) is a unique number system created by Ordnance Survey and used by housing providers and various industries across the UK. An example UPRN is 10010457355.
The UPRN may not be the same as the property reference assigned by your organisation.
If you don’t know the UPRN you can enter the address of the property instead on the next screen."
+ question_text: "Do you know the property's UPRN?"
+ uprn:
+ check_answer_label: "UPRN"
+ check_answer_prompt: ""
+ hint_text: ""
+ question_text: "What is the property's UPRN?"
+
+ uprn_confirmed:
+ page_header: "We found an address that might be this property"
+ check_answer_label: "Is this the right address?"
+ check_answer_prompt: "Tell us if this is the right address"
+ hint_text: ""
+ question_text: "Is this the property address?"
+
+ address_matcher:
+ page_header: "Find an address"
+ address_line1_input:
+ check_answer_label: "Find address"
+ check_answer_prompt: "Try find address"
+ hint_text: ""
+ question_text: "Address line 1"
+ postcode_full_input:
+ check_answer_label: ""
+ check_answer_prompt: ""
+ hint_text: ""
+ question_text: "Postcode"
+
+ uprn_selection:
+ page_header: "We found an address that might be this property"
+ check_answer_label: "Select correct address"
+ check_answer_prompt: "Select correct address"
+ hint_text: ""
+ question_text: "Select the correct address"
address:
page_header: "What is the property's address?"
diff --git a/config/locales/validations/sales/property_information.en.yml b/config/locales/validations/sales/property_information.en.yml
index f421177af..9014f1d78 100644
--- a/config/locales/validations/sales/property_information.en.yml
+++ b/config/locales/validations/sales/property_information.en.yml
@@ -7,7 +7,7 @@ en:
joint_purchase: "Buyers’ last accommodation and discounted ownership postcodes must match."
not_joint_purchase: "Buyer’s last accommodation and discounted ownership postcodes must match."
invalid: "Enter a postcode in the correct format, for example AA1 1AA."
- not_in_england: "It looks like you have entered a postcode outside of England. Only create logs for sales in England."
+ not_in_england: "It looks like you have entered a postcode outside of England - only submit Lettings forms for Lettings that occur in England"
ppostcode_full:
postcode_must_match_previous:
joint_purchase: "Buyers’ last accommodation and discounted ownership postcodes must match."
@@ -21,7 +21,7 @@ en:
joint_purchase: "Buyers’ last accommodation and discounted ownership postcodes must match."
not_joint_purchase: "Buyer’s last accommodation and discounted ownership postcodes must match."
invalid: "UPRN must be 12 digits or less."
- not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
+ not_in_england: "It looks like you have an entered a postcode outside of England. Only create logs for lettings in England."
beds:
bedsits_have_max_one_bedroom: "Number of bedrooms must be 1 if the property is a bedsit."
proptype:
@@ -29,11 +29,11 @@ en:
uprn_known:
invalid: "You must answer UPRN known?"
la:
- not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
+ not_in_england: "It looks like you have entered an address outside of England. Only create logs for lettings in England."
uprn_confirmation:
- not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
+ not_in_england: "It looks like you have entered an address outside of England. Only create logs for lettings in England."
uprn_selection:
- not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
+ not_in_england: "It looks like you have entered an address outside of England. Only create logs for lettings in England."
saledate:
- postcode_not_in_england: "It looks like you have entered a postcode outside of England. Only create logs for sales in England."
- address_not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
+ postcode_not_in_england: "It looks like you have an entered a postcode outside of England. Only create logs for lettings in England."
+ address_not_in_england: "It looks like you have entered an address outside of England. Only create logs for lettings in England."
diff --git a/config/routes.rb b/config/routes.rb
index 304d54ef0..471c89578 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -39,10 +39,6 @@ Rails.application.routes.draw do
get "/data-sharing-agreement", to: "content#data_sharing_agreement"
get "/service-moved", to: "maintenance#service_moved"
get "/service-unavailable", to: "maintenance#service_unavailable"
- get "/address-search", to: "address_search#index"
- get "/address-search/current", to: "address_search#current"
- get "/address-search/manual-input/:log_type/:log_id", to: "address_search#manual_input", as: "address_manual_input"
- get "/address-search/search-input/:log_type/:log_id", to: "address_search#search_input", as: "address_search_input"
get "collection-resources", to: "collection_resources#index"
get "/collection-resources/:log_type/:year/:resource_type/download", to: "collection_resources#download_mandatory_collection_resource", as: :download_mandatory_collection_resource
diff --git a/db/migrate/20250219122817_add_manual_address_entry_selected_to_logs.rb b/db/migrate/20250219122817_add_manual_address_entry_selected_to_logs.rb
deleted file mode 100644
index a0d0f7529..000000000
--- a/db/migrate/20250219122817_add_manual_address_entry_selected_to_logs.rb
+++ /dev/null
@@ -1,6 +0,0 @@
-class AddManualAddressEntrySelectedToLogs < ActiveRecord::Migration[7.2]
- def change
- add_column :sales_logs, :manual_address_entry_selected, :boolean, default: false
- add_column :lettings_logs, :manual_address_entry_selected, :boolean, default: false
- end
-end
diff --git a/db/schema.rb b/db/schema.rb
index f041f506e..894bb1638 100644
--- a/db/schema.rb
+++ b/db/schema.rb
@@ -10,7 +10,7 @@
#
# It's strongly recommended that you check this file into your version control system.
-ActiveRecord::Schema[7.2].define(version: 2025_02_19_122817) do
+ActiveRecord::Schema[7.2].define(version: 2025_01_10_150609) do
# These are extensions that must be enabled in order to support this database
enable_extension "plpgsql"
@@ -373,7 +373,6 @@ ActiveRecord::Schema[7.2].define(version: 2025_02_19_122817) do
t.integer "partner_under_16_value_check"
t.integer "multiple_partners_value_check"
t.bigint "created_by_id"
- t.boolean "manual_address_entry_selected", default: false
t.index ["assigned_to_id"], name: "index_lettings_logs_on_assigned_to_id"
t.index ["bulk_upload_id"], name: "index_lettings_logs_on_bulk_upload_id"
t.index ["created_by_id"], name: "index_lettings_logs_on_created_by_id"
@@ -770,7 +769,6 @@ ActiveRecord::Schema[7.2].define(version: 2025_02_19_122817) do
t.decimal "mrentprestaircasing", precision: 10, scale: 2
t.datetime "lasttransaction"
t.datetime "initialpurchase"
- t.boolean "manual_address_entry_selected", default: false
t.index ["assigned_to_id"], name: "index_sales_logs_on_assigned_to_id"
t.index ["bulk_upload_id"], name: "index_sales_logs_on_bulk_upload_id"
t.index ["created_by_id"], name: "index_sales_logs_on_created_by_id"
diff --git a/spec/factories/lettings_log.rb b/spec/factories/lettings_log.rb
index 1581527d0..c8c51ecf3 100644
--- a/spec/factories/lettings_log.rb
+++ b/spec/factories/lettings_log.rb
@@ -6,7 +6,6 @@ FactoryBot.define do
managing_organisation { assigned_to.organisation }
created_at { Time.zone.today }
updated_at { Time.zone.today }
- manual_address_entry_selected { true }
before(:create) do |log, _evaluator|
if log.period && !log.managing_organisation.organisation_rent_periods.exists?(rent_period: log.period)
@@ -167,11 +166,13 @@ FactoryBot.define do
town_or_city { Faker::Address.city }
ppcodenk { 1 }
tshortfall_known { 1 }
- after(:build) do |log, evaluator|
+ after(:build) do |log, _evaluator|
if log.startdate >= Time.zone.local(2024, 4, 1)
+ log.address_line1_input = log.address_line1
+ log.postcode_full_input = log.postcode_full
log.nationality_all_group = 826
- log.uprn = evaluator.uprn || "10033558653"
- log.uprn_selection = evaluator.uprn_selection || "10033558653"
+ log.uprn = "10033558653"
+ log.uprn_selection = 1
end
end
end
diff --git a/spec/factories/sales_log.rb b/spec/factories/sales_log.rb
index 64137704c..820c99fdc 100644
--- a/spec/factories/sales_log.rb
+++ b/spec/factories/sales_log.rb
@@ -8,8 +8,6 @@ FactoryBot.define do
managing_organisation { assigned_to.organisation }
created_at { Time.zone.now }
updated_at { Time.zone.now }
- manual_address_entry_selected { true }
-
trait :in_progress do
purchid { "PC123" }
ownershipsch { 2 }
@@ -168,12 +166,14 @@ FactoryBot.define do
nationalbuy2 { 13 }
buy2living { 3 }
proplen_asked { 1 }
- after(:build) do |log, evaluator|
+ after(:build) do |log, _evaluator|
if log.saledate >= Time.zone.local(2024, 4, 1)
+ log.address_line1_input = log.address_line1
+ log.postcode_full_input = log.postcode_full
log.nationality_all_group = 826
log.nationality_all_buyer2_group = 826
- log.uprn = evaluator.uprn || "10033558653"
- log.uprn_selection = evaluator.uprn_selection || "10033558653"
+ log.uprn = "10033558653"
+ log.uprn_selection = 1
end
if log.saledate >= Time.zone.local(2025, 4, 1)
log.relat2 = "X" if log.relat2 == "C"
diff --git a/spec/features/form/address_search_spec.rb b/spec/features/form/address_search_spec.rb
deleted file mode 100644
index cd1738195..000000000
--- a/spec/features/form/address_search_spec.rb
+++ /dev/null
@@ -1,45 +0,0 @@
-require "rails_helper"
-require_relative "helpers"
-
-RSpec.describe "Address Search" do
- include Helpers
- let(:user) { FactoryBot.create(:user) }
- let(:sales_log) do
- FactoryBot.create(
- :sales_log,
- :shared_ownership_setup_complete,
- assigned_to: user,
- manual_address_entry_selected: false,
- )
- end
-
- before do
- sign_in user
- end
-
- context "when using address search feature" do
- before do
- visit("/sales-logs/#{sales_log.id}/address-search")
- end
-
- it "allows searching by a UPRN", js: true do
- find("#sales-log-uprn-field").click.native.send_keys("1", "0", "0", "3", "3", "5", "4", "4", "6", "1", "4", :down)
- expect(find("#sales-log-uprn-field").value).to eq("10033544614")
- end
-
- it "allows searching by address", js: true do
- find("#sales-log-uprn-field").click.native.send_keys("S", "W", "1", "5", :down, :enter)
- expect(find("#sales-log-uprn-field").value).to eq("SW15")
- end
-
- it "displays the placeholder text", js: true do
- expect(find("#sales-log-uprn-field")["placeholder"]).to eq("Start typing to search")
- end
-
- it "displays correct bottom guidance text" do
- find("span.govuk-details__summary-text", text: "Can’t find the address you’re looking for?").click
- expect(page).to have_content("Some properties may not be available yet e.g. new builds; you might need to enter them manually instead")
- expect(page).to have_content("For UPRN (Unique Property Reference Number), please enter the full value exactly")
- end
- end
-end
diff --git a/spec/features/form/form_navigation_spec.rb b/spec/features/form/form_navigation_spec.rb
index 695115a78..6484fe94c 100644
--- a/spec/features/form/form_navigation_spec.rb
+++ b/spec/features/form/form_navigation_spec.rb
@@ -186,4 +186,64 @@ RSpec.describe "Form Navigation" do
expect(page).to have_current_path("/lettings-logs/#{id}/duplicate-logs?original_log_id=#{id}")
end
end
+
+ describe "searching for an address" do
+ let(:now) { Time.zone.local(2024, 5, 1) }
+
+ context "with a lettings log" do
+ let(:lettings_log) { create(:lettings_log, :setup_completed, startdate: Time.zone.local(2024, 5, 5), assigned_to: user) }
+
+ before do
+ stub_request(:get, /api\.os\.uk/)
+ .to_return(status: 200, body: { results: [{ DPA: { MATCH: 0.9, BUILDING_NAME: "result address line 1", POST_TOWN: "result town or city", POSTCODE: "AA1 1AA", UPRN: "12345" } }] }.to_json, headers: {})
+ end
+
+ it "allows searching for an address" do
+ visit("lettings-logs/#{id}/address-matcher")
+ fill_in("lettings-log-address-line1-input-field", with: "address")
+ fill_in("lettings-log-postcode-full-input-field", with: "A1 1AA")
+ click_button(text: "Search")
+ expect(page).to have_current_path("/lettings-logs/#{id}/uprn-selection")
+ end
+
+ it "allows searching for an address from check your answers page" do
+ visit("lettings-logs/#{id}/address-matcher?referrer=check_answers")
+ fill_in("lettings-log-address-line1-input-field", with: "address")
+ fill_in("lettings-log-postcode-full-input-field", with: "A1 1AA")
+ click_button(text: "Search")
+ expect(page).to have_current_path("/lettings-logs/#{id}/uprn-selection?referrer=check_answers&unanswered_pages=property_local_authority")
+ choose("lettings-log-uprn-selection-12345-field", allow_label_click: true)
+ click_button(text: "Save changes")
+ expect(page).to have_current_path("/lettings-logs/#{id}/property-information/check-answers")
+ end
+ end
+
+ context "with a sales log" do
+ let(:sales_log) { create(:sales_log, :outright_sale_setup_complete, saledate: Time.zone.local(2024, 5, 5), assigned_to: user) }
+
+ before do
+ stub_request(:get, /api\.os\.uk/)
+ .to_return(status: 200, body: { results: [{ DPA: { MATCH: 0.9, BUILDING_NAME: "result address line 1", POST_TOWN: "result town or city", POSTCODE: "AA1 1AA", UPRN: "12345" } }] }.to_json, headers: {})
+ end
+
+ it "allows searching for an address" do
+ visit("sales-logs/#{sales_log.id}/address-matcher")
+ fill_in("sales-log-address-line1-input-field", with: "address")
+ fill_in("sales-log-postcode-full-input-field", with: "A1 1AA")
+ click_button(text: "Search")
+ expect(page).to have_current_path("/sales-logs/#{sales_log.id}/uprn-selection")
+ end
+
+ it "allows searching for an address from check your answers page" do
+ visit("sales-logs/#{sales_log.id}/address-matcher?referrer=check_answers")
+ fill_in("sales-log-address-line1-input-field", with: "address")
+ fill_in("sales-log-postcode-full-input-field", with: "A1 1AA")
+ click_button(text: "Search")
+ expect(page).to have_current_path("/sales-logs/#{sales_log.id}/uprn-selection?referrer=check_answers&unanswered_pages=property_local_authority")
+ choose("sales-log-uprn-selection-12345-field", allow_label_click: true)
+ click_button(text: "Save changes")
+ expect(page).to have_current_path("/sales-logs/#{sales_log.id}/property-information/check-answers")
+ end
+ end
+ end
end
diff --git a/spec/features/lettings_log_spec.rb b/spec/features/lettings_log_spec.rb
index 15d24e5ed..a400ef2d0 100644
--- a/spec/features/lettings_log_spec.rb
+++ b/spec/features/lettings_log_spec.rb
@@ -729,5 +729,380 @@ RSpec.describe "Lettings Log Features" do
expect(duplicate_log.duplicate_set_id).to be_nil
end
end
+
+ context "when filling out address fields" do
+ let(:lettings_log) { create(:lettings_log, :setup_completed, assigned_to: user) }
+
+ before do
+ body = {
+ results: [
+ {
+ DPA: {
+ "POSTCODE": "AA1 1AA",
+ "POST_TOWN": "Bristol",
+ "ORGANISATION_NAME": "Some place",
+ },
+ },
+ ],
+ }.to_json
+
+ WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/uprn?dataset=DPA,LPI&key=OS_DATA_KEY&uprn=111")
+ .to_return(status: 200, body:, headers: {})
+
+ body = { results: [{ DPA: { UPRN: "111" } }] }.to_json
+ WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?query=Address+line+1%2C+AA1+1AA&key=OS_DATA_KEY&maxresults=10&minmatch=0.4")
+ .to_return(status: 200, body:, headers: {})
+
+ WebMock.stub_request(:get, "https://api.postcodes.io/postcodes/AA11AA")
+ .to_return(status: 200, body: "{\"status\":200,\"result\":{\"postcode\":\"AA1 1AA\",\"admin_district\":\"Westminster\",\"codes\":{\"admin_district\":\"E09000033\"}}}", headers: {})
+
+ WebMock.stub_request(:get, "https://api.postcodes.io/postcodes/AA12AA")
+ .to_return(status: 200, body: "{\"status\":200,\"result\":{\"postcode\":\"AA1 2AA\",\"admin_district\":\"Wigan\",\"codes\":{\"admin_district\":\"E08000010\"}}}", headers: {})
+
+ body = { results: [] }.to_json
+ WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?query=Address+line+1%2C+AA1+1AB&key=OS_DATA_KEY&maxresults=10&minmatch=0.4")
+ .to_return(status: 200, body:, headers: {})
+
+ visit("/lettings-logs/#{lettings_log.id}/uprn")
+ end
+
+ context "and uprn is known and answered" do
+ before do
+ choose "Yes"
+ fill_in("lettings_log[uprn]", with: "111")
+ click_button("Save and continue")
+ end
+
+ context "and uprn is confirmed" do
+ it "sets correct address fields" do
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(1) # yes
+ expect(lettings_log.uprn).to eq("111")
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(1)
+ expect(lettings_log.postcode_full).to eq("AA1 1AA")
+ expect(lettings_log.address_line1).to eq("Some Place")
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq("Bristol")
+ expect(lettings_log.address_line1_input).to eq(nil)
+ expect(lettings_log.postcode_full_input).to eq(nil)
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq("E09000033")
+
+ choose "Yes"
+ click_button("Save and continue")
+
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(1) # yes
+ expect(lettings_log.uprn).to eq("111")
+ expect(lettings_log.uprn_confirmed).to eq(1) # yes
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(1)
+ expect(lettings_log.postcode_full).to eq("AA1 1AA")
+ expect(lettings_log.address_line1).to eq("Some Place")
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq("Bristol")
+ expect(lettings_log.address_line1_input).to eq(nil)
+ expect(lettings_log.postcode_full_input).to eq(nil)
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq("E09000033")
+ end
+
+ context "and changes to uprn not known" do
+ it "sets correct address fields" do
+ visit("/lettings-logs/#{lettings_log.id}/uprn")
+
+ choose "No"
+ click_button("Save and continue")
+
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(0) # no
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(nil)
+ expect(lettings_log.postcode_full).to eq(nil)
+ expect(lettings_log.address_line1).to eq(nil)
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.address_line1_input).to eq(nil)
+ expect(lettings_log.postcode_full_input).to eq(nil)
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq(nil)
+ end
+ end
+ end
+
+ context "and uprn is not confirmed" do
+ before do
+ choose "No, I want to search for the address instead"
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ lettings_log.reload
+
+ expect(lettings_log.uprn_known).to eq(0) # no
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(nil)
+ expect(lettings_log.postcode_full).to eq(nil)
+ expect(lettings_log.address_line1).to eq(nil)
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.address_line1_input).to eq(nil)
+ expect(lettings_log.postcode_full_input).to eq(nil)
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq(nil)
+ end
+ end
+ end
+
+ context "and uprn is not known" do
+ before do
+ choose "No"
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(0) # no
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(nil)
+ expect(lettings_log.postcode_full).to eq(nil)
+ expect(lettings_log.address_line1).to eq(nil)
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.address_line1_input).to eq(nil)
+ expect(lettings_log.postcode_full_input).to eq(nil)
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq(nil)
+ end
+
+ context "and the address is not found" do
+ it "sets correct address fields" do
+ fill_in("lettings_log[address_line1_input]", with: "Address line 1")
+ fill_in("lettings_log[postcode_full_input]", with: "AA1 1AB")
+ click_button("Search")
+
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(0) # no
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(nil)
+ expect(lettings_log.postcode_full).to eq(nil)
+ expect(lettings_log.address_line1).to eq(nil)
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.address_line1_input).to eq("Address line 1")
+ expect(lettings_log.postcode_full_input).to eq("AA1 1AB")
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq(nil)
+
+ click_button("Confirm and continue")
+
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(0) # no
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(nil)
+ expect(lettings_log.postcode_full).to eq(nil)
+ expect(lettings_log.address_line1).to eq(nil)
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.address_line1_input).to eq("Address line 1")
+ expect(lettings_log.postcode_full_input).to eq("AA1 1AB")
+ expect(lettings_log.address_search_value_check).to eq(0)
+ expect(lettings_log.la).to eq(nil)
+ end
+ end
+
+ context "and address is found, re-searched and not found" do
+ before do
+ fill_in("lettings_log[address_line1_input]", with: "Address line 1")
+ fill_in("lettings_log[postcode_full_input]", with: "AA1 1AA")
+ click_button("Search")
+ visit("/lettings-logs/#{lettings_log.id}/address-matcher")
+
+ fill_in("lettings_log[address_line1_input]", with: "Address line 1")
+ fill_in("lettings_log[postcode_full_input]", with: "AA1 1AB")
+ click_button("Search")
+ end
+
+ it "routes to the correct page" do
+ expect(page).to have_current_path("/lettings-logs/#{lettings_log.id}/no-address-found")
+ end
+ end
+
+ context "and the user selects 'address_not_listed'" do
+ before do
+ fill_in("lettings_log[address_line1_input]", with: "Address line 1")
+ fill_in("lettings_log[postcode_full_input]", with: "AA1 1AA")
+ click_button("Search")
+ choose "The address is not listed, I want to enter the address manually"
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(0) # no
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq("uprn_not_listed")
+ expect(lettings_log.postcode_known).to eq(1)
+ expect(lettings_log.postcode_full).to eq("AA1 1AA")
+ expect(lettings_log.address_line1).to eq("Address line 1")
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.address_line1_input).to eq("Address line 1")
+ expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq("E09000033")
+ end
+
+ context "and the user enters a new address manually" do
+ context "without changing a valid postcode" do
+ before do
+ fill_in("lettings_log[town_or_city]", with: "Town")
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(0) # no
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq("uprn_not_listed")
+ expect(lettings_log.postcode_known).to eq(1)
+ expect(lettings_log.postcode_full).to eq("AA1 1AA")
+ expect(lettings_log.address_line1).to eq("Address line 1")
+ expect(lettings_log.address_line2).to eq("")
+ expect(lettings_log.town_or_city).to eq("Town")
+ expect(lettings_log.address_line1_input).to eq("Address line 1")
+ expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq("E09000033")
+ end
+ end
+
+ context "with changing the postcode" do
+ before do
+ fill_in("lettings_log[town_or_city]", with: "Town")
+ fill_in("lettings_log[postcode_full]", with: "AA12AA")
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(0) # no
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq("uprn_not_listed")
+ expect(lettings_log.postcode_known).to eq(1)
+ expect(lettings_log.postcode_full).to eq("AA1 2AA")
+ expect(lettings_log.address_line1).to eq("Address line 1")
+ expect(lettings_log.address_line2).to eq("")
+ expect(lettings_log.town_or_city).to eq("Town")
+ expect(lettings_log.address_line1_input).to eq("Address line 1")
+ expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq("E08000010")
+ end
+ end
+ end
+ end
+
+ context "and the user selects 'address_not_listed' when partial postcode is entered" do
+ before do
+ fill_in("lettings_log[address_line1_input]", with: "Address line 1")
+ fill_in("lettings_log[postcode_full_input]", with: "AA1")
+ click_button("Search")
+ choose "The address is not listed, I want to enter the address manually"
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(0) # no
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq("uprn_not_listed")
+ expect(lettings_log.postcode_known).to eq(nil)
+ expect(lettings_log.postcode_full).to eq(nil)
+ expect(lettings_log.address_line1).to eq("Address line 1")
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.address_line1_input).to eq("Address line 1")
+ expect(lettings_log.postcode_full_input).to eq("AA1")
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq(nil)
+ end
+ end
+
+ context "and the user selects 'address_not_listed' and then changes their mind and selects an address" do
+ before do
+ fill_in("lettings_log[address_line1_input]", with: "Address line 1")
+ fill_in("lettings_log[postcode_full_input]", with: "AA1 1AA")
+ click_button("Search")
+ choose "The address is not listed, I want to enter the address manually"
+ click_button("Save and continue")
+
+ visit("/lettings-logs/#{lettings_log.id}/uprn-selection")
+ choose("lettings-log-uprn-selection-111-field", allow_label_click: true)
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(1)
+ expect(lettings_log.uprn).to eq("111")
+ expect(lettings_log.uprn_confirmed).to eq(1)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(1)
+ expect(lettings_log.postcode_full).to eq("AA1 1AA")
+ expect(lettings_log.address_line1).to eq("Some Place")
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq("Bristol")
+ expect(lettings_log.address_line1_input).to eq("Address line 1")
+ expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq("E09000033")
+ end
+ end
+
+ context "and possible addresses found and selected" do
+ before do
+ fill_in("lettings_log[address_line1_input]", with: "Address line 1")
+ fill_in("lettings_log[postcode_full_input]", with: "AA1 1AA")
+ click_button("Search")
+ choose("lettings-log-uprn-selection-111-field", allow_label_click: true)
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(1)
+ expect(lettings_log.uprn).to eq("111")
+ expect(lettings_log.uprn_confirmed).to eq(1)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(1)
+ expect(lettings_log.postcode_full).to eq("AA1 1AA")
+ expect(lettings_log.address_line1).to eq("Some Place")
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq("Bristol")
+ expect(lettings_log.address_line1_input).to eq("Address line 1")
+ expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
+ expect(lettings_log.address_search_value_check).to eq(nil)
+ expect(lettings_log.la).to eq("E09000033")
+ end
+ end
+ end
+ end
end
end
diff --git a/spec/features/sales_log_spec.rb b/spec/features/sales_log_spec.rb
index 3fa89a504..3030d6d6a 100644
--- a/spec/features/sales_log_spec.rb
+++ b/spec/features/sales_log_spec.rb
@@ -334,6 +334,381 @@ RSpec.describe "Sales Log Features" do
expect(page).to have_current_path("/sales-logs/bulk-uploads")
end
end
+
+ context "when filling out address fields" do
+ let(:sales_log) { create(:sales_log, :shared_ownership_setup_complete, assigned_to: user) }
+
+ before do
+ body = {
+ results: [
+ {
+ DPA: {
+ "POSTCODE": "AA1 1AA",
+ "POST_TOWN": "Bristol",
+ "ORGANISATION_NAME": "Some place",
+ },
+ },
+ ],
+ }.to_json
+
+ WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/uprn?dataset=DPA,LPI&key=OS_DATA_KEY&uprn=111")
+ .to_return(status: 200, body:, headers: {})
+
+ body = { results: [{ DPA: { UPRN: "111" } }] }.to_json
+ WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?query=Address+line+1%2C+AA1+1AA&key=OS_DATA_KEY&maxresults=10&minmatch=0.4")
+ .to_return(status: 200, body:, headers: {})
+
+ WebMock.stub_request(:get, "https://api.postcodes.io/postcodes/AA11AA")
+ .to_return(status: 200, body: "{\"status\":200,\"result\":{\"postcode\":\"AA1 1AA\",\"admin_district\":\"Westminster\",\"codes\":{\"admin_district\":\"E09000033\"}}}", headers: {})
+
+ WebMock.stub_request(:get, "https://api.postcodes.io/postcodes/AA12AA")
+ .to_return(status: 200, body: "{\"status\":200,\"result\":{\"postcode\":\"AA1 2AA\",\"admin_district\":\"Wigan\",\"codes\":{\"admin_district\":\"E08000010\"}}}", headers: {})
+
+ body = { results: [] }.to_json
+ WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?query=Address+line+1%2C+AA1+1AB&key=OS_DATA_KEY&maxresults=10&minmatch=0.4")
+ .to_return(status: 200, body:, headers: {})
+
+ visit("/sales-logs/#{sales_log.id}/uprn")
+ end
+
+ context "and uprn is known and answered" do
+ before do
+ choose "Yes"
+ fill_in("sales_log[uprn]", with: "111")
+ click_button("Save and continue")
+ end
+
+ context "and uprn is confirmed" do
+ it "sets correct address fields" do
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(1) # yes
+ expect(sales_log.uprn).to eq("111")
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(0)
+ expect(sales_log.postcode_full).to eq("AA1 1AA")
+ expect(sales_log.address_line1).to eq("Some Place")
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq("Bristol")
+ expect(sales_log.address_line1_input).to eq(nil)
+ expect(sales_log.postcode_full_input).to eq(nil)
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq("E09000033")
+
+ choose "Yes"
+ click_button("Save and continue")
+
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(1) # yes
+ expect(sales_log.uprn).to eq("111")
+ expect(sales_log.uprn_confirmed).to eq(1) # yes
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(0)
+ expect(sales_log.postcode_full).to eq("AA1 1AA")
+ expect(sales_log.address_line1).to eq("Some Place")
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq("Bristol")
+ expect(sales_log.address_line1_input).to eq(nil)
+ expect(sales_log.postcode_full_input).to eq(nil)
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq("E09000033")
+ end
+
+ context "and changes to uprn not known" do
+ it "sets correct address fields" do
+ visit("/sales-logs/#{sales_log.id}/uprn")
+
+ choose "No"
+ click_button("Save and continue")
+
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(0) # no
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(nil)
+ expect(sales_log.postcode_full).to eq(nil)
+ expect(sales_log.address_line1).to eq(nil)
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.address_line1_input).to eq(nil)
+ expect(sales_log.postcode_full_input).to eq(nil)
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq(nil)
+ end
+ end
+ end
+
+ context "and uprn is not confirmed" do
+ before do
+ choose "No, I want to search for the address instead"
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ sales_log.reload
+
+ expect(sales_log.uprn_known).to eq(0) # no
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(nil)
+ expect(sales_log.postcode_full).to eq(nil)
+ expect(sales_log.address_line1).to eq(nil)
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.address_line1_input).to eq(nil)
+ expect(sales_log.postcode_full_input).to eq(nil)
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq(nil)
+ end
+ end
+ end
+
+ context "and uprn is not known" do
+ before do
+ choose "No"
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(0) # no
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(nil)
+ expect(sales_log.postcode_full).to eq(nil)
+ expect(sales_log.address_line1).to eq(nil)
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.address_line1_input).to eq(nil)
+ expect(sales_log.postcode_full_input).to eq(nil)
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq(nil)
+ end
+
+ context "and the address is not found" do
+ it "sets correct address fields" do
+ fill_in("sales_log[address_line1_input]", with: "Address line 1")
+ fill_in("sales_log[postcode_full_input]", with: "AA1 1AB")
+ click_button("Search")
+
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(0) # no
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(nil)
+ expect(sales_log.postcode_full).to eq(nil)
+ expect(sales_log.address_line1).to eq(nil)
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.address_line1_input).to eq("Address line 1")
+ expect(sales_log.postcode_full_input).to eq("AA1 1AB")
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq(nil)
+
+ click_button("Confirm and continue")
+
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(0) # no
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(nil)
+ expect(sales_log.postcode_full).to eq(nil)
+ expect(sales_log.address_line1).to eq(nil)
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.address_line1_input).to eq("Address line 1")
+ expect(sales_log.postcode_full_input).to eq("AA1 1AB")
+ expect(sales_log.address_search_value_check).to eq(0)
+ expect(sales_log.la).to eq(nil)
+ end
+ end
+
+ context "and address is found, re-searched and not found" do
+ before do
+ fill_in("sales_log[address_line1_input]", with: "Address line 1")
+ fill_in("sales_log[postcode_full_input]", with: "AA1 1AA")
+ click_button("Search")
+ visit("/sales-logs/#{sales_log.id}/address-matcher")
+
+ fill_in("sales_log[address_line1_input]", with: "Address line 1")
+ fill_in("sales_log[postcode_full_input]", with: "AA1 1AB")
+ click_button("Search")
+ end
+
+ it "routes to the correct page" do
+ expect(page).to have_current_path("/sales-logs/#{sales_log.id}/no-address-found")
+ end
+ end
+
+ context "and the user selects 'address_not_listed'" do
+ before do
+ fill_in("sales_log[address_line1_input]", with: "Address line 1")
+ fill_in("sales_log[postcode_full_input]", with: "AA1 1AA")
+ click_button("Search")
+ choose "The address is not listed, I want to enter the address manually"
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(0) # no
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq("uprn_not_listed")
+ expect(sales_log.pcodenk).to eq(0)
+ expect(sales_log.postcode_full).to eq("AA1 1AA")
+ expect(sales_log.address_line1).to eq("Address line 1")
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.address_line1_input).to eq("Address line 1")
+ expect(sales_log.postcode_full_input).to eq("AA1 1AA")
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq("E09000033")
+ end
+
+ context "and the user enters a new address manually" do
+ context "without changing a valid postcode" do
+ before do
+ fill_in("sales_log[town_or_city]", with: "Town")
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(0) # no
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq("uprn_not_listed")
+ expect(sales_log.pcodenk).to eq(0)
+ expect(sales_log.postcode_full).to eq("AA1 1AA")
+ expect(sales_log.address_line1).to eq("Address line 1")
+ expect(sales_log.address_line2).to eq("")
+ expect(sales_log.town_or_city).to eq("Town")
+ expect(sales_log.address_line1_input).to eq("Address line 1")
+ expect(sales_log.postcode_full_input).to eq("AA1 1AA")
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq("E09000033")
+ end
+ end
+
+ context "with changing the postcode" do
+ before do
+ fill_in("sales_log[town_or_city]", with: "Town")
+ fill_in("sales_log[postcode_full]", with: "AA12AA")
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(0) # no
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq("uprn_not_listed")
+ expect(sales_log.pcodenk).to eq(0)
+ expect(sales_log.postcode_full).to eq("AA1 2AA")
+ expect(sales_log.address_line1).to eq("Address line 1")
+ expect(sales_log.address_line2).to eq("")
+ expect(sales_log.town_or_city).to eq("Town")
+ expect(sales_log.address_line1_input).to eq("Address line 1")
+ expect(sales_log.postcode_full_input).to eq("AA1 1AA")
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq("E08000010")
+ end
+ end
+ end
+ end
+
+ context "and the user selects 'address_not_listed' when partial postcode is given" do
+ before do
+ fill_in("sales_log[address_line1_input]", with: "Address line 1")
+ fill_in("sales_log[postcode_full_input]", with: "1AA")
+ click_button("Search")
+ choose "The address is not listed, I want to enter the address manually"
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(0) # no
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq("uprn_not_listed")
+ expect(sales_log.pcodenk).to eq(nil)
+ expect(sales_log.postcode_full).to eq(nil)
+ expect(sales_log.address_line1).to eq("Address line 1")
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.address_line1_input).to eq("Address line 1")
+ expect(sales_log.postcode_full_input).to eq("1AA")
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq(nil)
+ end
+ end
+
+ context "and the user selects 'address_not_listed' and then changes their mind and selects an address" do
+ before do
+ fill_in("sales_log[address_line1_input]", with: "Address line 1")
+ fill_in("sales_log[postcode_full_input]", with: "AA1 1AA")
+ click_button("Search")
+ choose "The address is not listed, I want to enter the address manually"
+ click_button("Save and continue")
+
+ visit("/sales-logs/#{sales_log.id}/uprn-selection")
+ choose("sales-log-uprn-selection-111-field", allow_label_click: true)
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(1)
+ expect(sales_log.uprn).to eq("111")
+ expect(sales_log.uprn_confirmed).to eq(1)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(0)
+ expect(sales_log.postcode_full).to eq("AA1 1AA")
+ expect(sales_log.address_line1).to eq("Some Place")
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq("Bristol")
+ expect(sales_log.address_line1_input).to eq("Address line 1")
+ expect(sales_log.postcode_full_input).to eq("AA1 1AA")
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq("E09000033")
+ end
+ end
+
+ context "and possible addresses found and selected" do
+ before do
+ fill_in("sales_log[address_line1_input]", with: "Address line 1")
+ fill_in("sales_log[postcode_full_input]", with: "AA1 1AA")
+ click_button("Search")
+ choose("sales-log-uprn-selection-111-field", allow_label_click: true)
+ click_button("Save and continue")
+ end
+
+ it "sets correct address fields" do
+ sales_log.reload
+ expect(sales_log.uprn_known).to eq(1)
+ expect(sales_log.uprn).to eq("111")
+ expect(sales_log.uprn_confirmed).to eq(1)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(0)
+ expect(sales_log.postcode_full).to eq("AA1 1AA")
+ expect(sales_log.address_line1).to eq("Some Place")
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq("Bristol")
+ expect(sales_log.address_line1_input).to eq("Address line 1")
+ expect(sales_log.postcode_full_input).to eq("AA1 1AA")
+ expect(sales_log.address_search_value_check).to eq(nil)
+ expect(sales_log.la).to eq("E09000033")
+ end
+ end
+ end
+ end
end
context "when a log becomes a duplicate" do
diff --git a/spec/fixtures/files/sales_logs_csv_export_codes_24.csv b/spec/fixtures/files/sales_logs_csv_export_codes_24.csv
index f874e4e75..e0ebccb38 100644
--- a/spec/fixtures/files/sales_logs_csv_export_codes_24.csv
+++ b/spec/fixtures/files/sales_logs_csv_export_codes_24.csv
@@ -1,3 +1,3 @@
Log ID,Status of log,ID of a set of duplicate logs,Time and date the log was created,Time and date the log was last updated,Year collection period opened,Was the log submitted in-service or via bulk upload?,ID of a set of bulk uploaded logs,Is the user in the created_by column the data protection officer?,Day of sale completion date,Month of sale completion date,Year of sale completion date,Which organisation owned this property before the sale?,Which organisation reported the sale?,User that created the log,User the log is assigned to,What is the purchaser code?,Was this purchase made through an ownership scheme?,What is the type of shared ownership/discounted ownership/outright sale?,"If type = 'Other', what is the type of outright sale?",Is the buyer a company?,Will the buyer(s) live in the property?,Is this a joint purchase?,Are there more than 2 joint buyers of this property?,Did you interview the buyer to answer these questions?,Has the buyer seen the MHCLG privacy notice?,What is the UPRN of the property?,Address line 1,Address line 2,Town/City,County,Postcode,The internal value to indicate if the LA was inferred from the postcode,LA name,LA code,UPRN of the address selected,Was the 'No address found' page seen?,Address line 1 input from address matching feature,Postcode input from address matching feature,Address line 1 entered in bulk upload file,Address line 2 entered in bulk upload file,Town or city entered in bulk upload file,County entered in bulk upload file,Postcode entered in bulk upload file,Local authority entered in bulk upload file,How many bedrooms does the property have?,What type of unit is the property?,Which type of building is the property?,Is the property built or adapted to wheelchair-user standards?,What is buyer 1's age?,Which of these best describes buyer 1's gender identity?,What is buyer 1's ethnic group?,Which of the following best describes buyer 1's ethnic background?,What is buyer 1's nationality?,Which of these best describes buyer 1's working situation?,Will buyer 1 live in the property?,What is buyer 2 or person 2's relationship to buyer 1?,What is buyer 2 or person 2's age?,Which of these best describes buyer 2 or person 2's gender identity?,What is buyer 2's ethnic group?,Which of the following best describes buyer 2's ethnic background?,What is buyer 2's nationality?,What is buyer 2 or person 2's working situation?,Will buyer 2 live in the property?,"Besides the buyer(s), how many other people live or will live in the property?",What is person 3's relationship to buyer 1?,What is person 3's age?,What is person 3's gender identity?,What is person 3's working situation?,What is person 4's relationship to buyer 1?,What is person 4's age?,What is person 4's gender identity?,What is person 4's working situation?,What is person 5's relationship to buyer 1?,What is person 5's age?,What is person 5's gender identity?,What is person 5's working situation?,What is person 6's relationship to buyer 1?,What is person 6's age?,What is person 6's gender identity?,What is person 6's working situation?,What was buyer 1's previous tenure?,Do you know the postcode of buyer 1's last settled accommodation?,Part 1 of postcode of buyer 1's last settled accommodation,Part 2 of postcode of buyer 1's last settled accommodation,Do you know the local authority of buyer 1's last settled accommodation?,The local authority code of buyer 1's last settled accommodation,The local authority name of buyer 1's last settled accommodation,Was the buyer registered with their PRP (HA)?,Was the buyer registered with another PRP (HA)?,Was the buyer registered with the local authority?,Was the buyer registered with a Help to Buy agent?,"Populated if pregyrha, pregother, pregla and pregghb are blank","At the time of purchase, was buyer 2 living at the same address as buyer 1?",What was buyer 2's previous tenure?,Have any of the buyers ever served as a regular in the UK armed forces?,Is the buyer still serving in the UK armed forces?,Are any of the buyers a spouse or civil partner of a UK armed forces regular who died in service within the last 2 years?,Does anyone in the household consider themselves to have a disability?,Does anyone in the household use a wheelchair?,Is buyer 1's annual income known?,What is buyer 1's annual income?,Was buyer 1's income used for a mortgage application?,Is buyer 1's annual income known?,What is buyer 2's annual income?,Was buyer 2's income used for a mortgage application?,Were the buyers receiving any of these housing-related benefits immediately before buying this property?,Is the the total amount the buyers had in savings known?,What is the total amount the buyers had in savings before they paid any deposit for the property?,Have any of the buyers previously owned a property?,Was the previous property under shared ownership?,How long did the buyer(s) live in the property before purchasing it?,Is this a staircasing transaction?,What percentage of the property has been bought in this staircasing transaction?,What percentage of the property do the buyers now own in total?,Was this transaction part of a back-to-back staircasing transaction to facilitate sale of the home on the open market?,Is this a resale?,Day of the exchange of contracts,Month of the exchange of contracts,Year of the exchange of contracts,Day of the practical completion or handover date,Month of the practical completion or handover date,Year of the practical completion or handover date,Was the household rehoused under a local authority nominations agreement?,"Was the buyer a private registered provider, housing association or local authority tenant immediately before this sale?",How many bedrooms did the buyer's previous property have?,What was the previous property type?,What was the rent type of buyer's previous tenure?,What is the full purchase price?,Populated if a soft validation is confirmed.,What was the initial percentage equity stake purchased?,Was a mortgage used to buy this property?,What is the mortgage amount?,What is the name of the mortgage lender?,"If mortgagelender = 'Other', what is the name of the mortgage lender?",What is the length of the mortgage in years?,Does this include any extra borrowing?,How much was the cash deposit paid on the property?,How much cash discount was given through Social Homebuy?,What is the basic monthly rent?,Does the property have any monthly leasehold charges?,What are the total monthly leasehold charges for the property?,Populated if a soft validation is confirmed.,What was the percentage discount?,"What was the amount of any loan, grant, discount or subsidy given?"
ID,STATUS,DUPLICATESET,CREATEDDATE,UPLOADDATE,COLLECTIONYEAR,CREATIONMETHOD,BULKUPLOADID,DATAPROTECT,DAY,MONTH,YEAR,OWNINGORGNAME,MANINGORGNAME,CREATEDBY,USERNAME,PURCHID,OWNERSHIP,TYPE,OTHTYPE,COMPANY,LIVEINBUYER,JOINT,JOINTMORE,NOINT,PRIVACYNOTICE,UPRN,ADDRESS1,ADDRESS2,TOWNCITY,COUNTY,POSTCODE,ISLAINFERRED,LANAME,LA,UPRNSELECTED,ADDRESS_SEARCH_VALUE_CHECK,ADDRESS1INPUT,POSTCODEINPUT,BULKADDRESS1,BULKADDRESS2,BULKTOWNCITY,BULKCOUNTY,BULKPOSTCODE,BULKLA,BEDS,PROPTYPE,BUILTYPE,WCHAIR,AGE1,SEX1,ETHNICGROUP1,ETHNIC,NATIONALITYALL1,ECSTAT1,LIVEINBUYER1,RELAT2,AGE2,SEX2,ETHNICGROUP2,ETHNIC2,NATIONALITYALL2,ECSTAT2,LIVEINBUYER2,HHTYPE,RELAT3,AGE3,SEX3,ECSTAT3,RELAT4,AGE4,SEX4,ECSTAT4,RELAT5,AGE5,SEX5,ECSTAT5,RELAT6,AGE6,SEX6,ECSTAT6,PREVTEN,PPCODENK,PPOSTC1,PPOSTC2,PREVIOUSLAKNOWN,PREVLOC,PREVLOCNAME,PREGYRHA,PREGOTHER,PREGLA,PREGGHB,PREGBLANK,BUY2LIVING,PREVTEN2,HHREGRES,HHREGRESSTILL,ARMEDFORCESSPOUSE,DISABLED,WHEEL,INC1NK,INCOME1,INC1MORT,INC2NK,INCOME2,INC2MORT,HB,SAVINGSNK,SAVINGS,PREVOWN,PREVSHARED,PROPLEN,STAIRCASE,STAIRBOUGHT,STAIROWNED,STAIRCASETOSALE,RESALE,EXDAY,EXMONTH,EXYEAR,HODAY,HOMONTH,HOYEAR,LANOMAGR,SOCTEN,FROMBEDS,FROMPROP,SOCPREVTEN,VALUE,VALUE_VALUE_CHECK,EQUITY,MORTGAGEUSED,MORTGAGE,MORTGAGELENDER,MORTGAGELENDEROTHER,MORTLEN1,EXTRABOR,DEPOSIT,CASHDIS,MRENT,HASMSCHARGE,MSCHARGE,MSCHARGE_VALUE_CHECK,DISCOUNT,GRANT
-,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,1,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,billyboy@eyeklaud.com,,2,8,,,,1,1,2,1,1,"1, Test Street",,Test Town,,AA1 1AA,true,Westminster,E09000033,1,,,,address line 1 as entered,address line 2 as entered,town or city as entered,county as entered,AB1 2CD,la as entered,2,1,1,1,30,X,17,17,826,1,1,P,35,X,17,,826,1,1,3,C,14,X,9,X,-9,X,3,R,-9,R,10,,,,,1,0,SW1A,1AA,1,E09000033,Westminster,1,1,1,1,,3,,1,4,5,1,1,0,13400,1,0,13400,1,4,1,,1,2,10,,,,,,,,,,,,,,,,,110000.0,,,1,20000.0,5,,10,1,80000.0,,,1,100.0,,,10000.0
+,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,1,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,billyboy@eyeklaud.com,,2,8,,,,1,1,2,1,1,"1, Test Street",,Test Town,,AA1 1AA,true,Westminster,E09000033,,,Address line 1,SW1A 1AA,address line 1 as entered,address line 2 as entered,town or city as entered,county as entered,AB1 2CD,la as entered,2,1,1,1,30,X,17,17,826,1,1,P,35,X,17,,826,1,1,3,C,14,X,9,X,-9,X,3,R,-9,R,10,,,,,1,0,SW1A,1AA,1,E09000033,Westminster,1,1,1,1,,3,,1,4,5,1,1,0,13400,1,0,13400,1,4,1,,1,2,10,,,,,,,,,,,,,,,,,110000.0,,,1,20000.0,5,,10,1,80000.0,,,1,100.0,,,10000.0
diff --git a/spec/fixtures/files/sales_logs_csv_export_labels_24.csv b/spec/fixtures/files/sales_logs_csv_export_labels_24.csv
index a66a16201..ffda37642 100644
--- a/spec/fixtures/files/sales_logs_csv_export_labels_24.csv
+++ b/spec/fixtures/files/sales_logs_csv_export_labels_24.csv
@@ -1,3 +1,3 @@
Log ID,Status of log,ID of a set of duplicate logs,Time and date the log was created,Time and date the log was last updated,Year collection period opened,Was the log submitted in-service or via bulk upload?,ID of a set of bulk uploaded logs,Is the user in the created_by column the data protection officer?,Day of sale completion date,Month of sale completion date,Year of sale completion date,Which organisation owned this property before the sale?,Which organisation reported the sale?,User that created the log,User the log is assigned to,What is the purchaser code?,Was this purchase made through an ownership scheme?,What is the type of shared ownership/discounted ownership/outright sale?,"If type = 'Other', what is the type of outright sale?",Is the buyer a company?,Will the buyer(s) live in the property?,Is this a joint purchase?,Are there more than 2 joint buyers of this property?,Did you interview the buyer to answer these questions?,Has the buyer seen the MHCLG privacy notice?,"What is the UPRN of the property?",Address line 1,Address line 2,Town/City,County,Postcode,The internal value to indicate if the LA was inferred from the postcode,LA name,LA code,UPRN of the address selected,Was the 'No address found' page seen?,Address line 1 input from address matching feature,Postcode input from address matching feature,Address line 1 entered in bulk upload file,Address line 2 entered in bulk upload file,Town or city entered in bulk upload file,County entered in bulk upload file,Postcode entered in bulk upload file,Local authority entered in bulk upload file,How many bedrooms does the property have?,What type of unit is the property?,Which type of building is the property?,Is the property built or adapted to wheelchair-user standards?,What is buyer 1's age?,Which of these best describes buyer 1's gender identity?,What is buyer 1's ethnic group?,Which of the following best describes buyer 1's ethnic background?,What is buyer 1's nationality?,Which of these best describes buyer 1's working situation?,Will buyer 1 live in the property?,What is buyer 2 or person 2's relationship to buyer 1?,What is buyer 2 or person 2's age?,Which of these best describes buyer 2 or person 2's gender identity?,What is buyer 2's ethnic group?,Which of the following best describes buyer 2's ethnic background?,What is buyer 2's nationality?,What is buyer 2 or person 2's working situation?,Will buyer 2 live in the property?,"Besides the buyer(s), how many other people live or will live in the property?",What is person 3's relationship to buyer 1?,What is person 3's age?,What is person 3's gender identity?,What is person 3's working situation?,What is person 4's relationship to buyer 1?,What is person 4's age?,What is person 4's gender identity?,What is person 4's working situation?,What is person 5's relationship to buyer 1?,What is person 5's age?,What is person 5's gender identity?,What is person 5's working situation?,What is person 6's relationship to buyer 1?,What is person 6's age?,What is person 6's gender identity?,What is person 6's working situation?,What was buyer 1's previous tenure?,Do you know the postcode of buyer 1's last settled accommodation?,Part 1 of postcode of buyer 1's last settled accommodation,Part 2 of postcode of buyer 1's last settled accommodation,Do you know the local authority of buyer 1's last settled accommodation?,The local authority code of buyer 1's last settled accommodation,The local authority name of buyer 1's last settled accommodation,Was the buyer registered with their PRP (HA)?,Was the buyer registered with another PRP (HA)?,Was the buyer registered with the local authority?,Was the buyer registered with a Help to Buy agent?,"Populated if pregyrha, pregother, pregla and pregghb are blank","At the time of purchase, was buyer 2 living at the same address as buyer 1?",What was buyer 2's previous tenure?,Have any of the buyers ever served as a regular in the UK armed forces?,Is the buyer still serving in the UK armed forces?,Are any of the buyers a spouse or civil partner of a UK armed forces regular who died in service within the last 2 years?,Does anyone in the household consider themselves to have a disability?,Does anyone in the household use a wheelchair?,Is buyer 1's annual income known?,What is buyer 1's annual income?,Was buyer 1's income used for a mortgage application?,Is buyer 1's annual income known?,What is buyer 2's annual income?,Was buyer 2's income used for a mortgage application?,Were the buyers receiving any of these housing-related benefits immediately before buying this property?,Is the the total amount the buyers had in savings known?,What is the total amount the buyers had in savings before they paid any deposit for the property?,Have any of the buyers previously owned a property?,Was the previous property under shared ownership?,How long did the buyer(s) live in the property before purchasing it?,Is this a staircasing transaction?,What percentage of the property has been bought in this staircasing transaction?,What percentage of the property do the buyers now own in total?,Was this transaction part of a back-to-back staircasing transaction to facilitate sale of the home on the open market?,Is this a resale?,Day of the exchange of contracts,Month of the exchange of contracts,Year of the exchange of contracts,Day of the practical completion or handover date,Month of the practical completion or handover date,Year of the practical completion or handover date,Was the household rehoused under a local authority nominations agreement?,"Was the buyer a private registered provider, housing association or local authority tenant immediately before this sale?",How many bedrooms did the buyer's previous property have?,What was the previous property type?,What was the rent type of buyer's previous tenure?,What is the full purchase price?,Populated if a soft validation is confirmed.,What was the initial percentage equity stake purchased?,Was a mortgage used to buy this property?,What is the mortgage amount?,What is the name of the mortgage lender?,"If mortgagelender = 'Other', what is the name of the mortgage lender?",What is the length of the mortgage in years?,Does this include any extra borrowing?,How much was the cash deposit paid on the property?,How much cash discount was given through Social Homebuy?,What is the basic monthly rent?,Does the property have any monthly leasehold charges?,What are the total monthly leasehold charges for the property?,Populated if a soft validation is confirmed.,What was the percentage discount?,"What was the amount of any loan, grant, discount or subsidy given?"
ID,STATUS,DUPLICATESET,CREATEDDATE,UPLOADDATE,COLLECTIONYEAR,CREATIONMETHOD,BULKUPLOADID,DATAPROTECT,DAY,MONTH,YEAR,OWNINGORGNAME,MANINGORGNAME,CREATEDBY,USERNAME,PURCHID,OWNERSHIP,TYPE,OTHTYPE,COMPANY,LIVEINBUYER,JOINT,JOINTMORE,NOINT,PRIVACYNOTICE,UPRN,ADDRESS1,ADDRESS2,TOWNCITY,COUNTY,POSTCODE,ISLAINFERRED,LANAME,LA,UPRNSELECTED,ADDRESS_SEARCH_VALUE_CHECK,ADDRESS1INPUT,POSTCODEINPUT,BULKADDRESS1,BULKADDRESS2,BULKTOWNCITY,BULKCOUNTY,BULKPOSTCODE,BULKLA,BEDS,PROPTYPE,BUILTYPE,WCHAIR,AGE1,SEX1,ETHNICGROUP1,ETHNIC,NATIONALITYALL1,ECSTAT1,LIVEINBUYER1,RELAT2,AGE2,SEX2,ETHNICGROUP2,ETHNIC2,NATIONALITYALL2,ECSTAT2,LIVEINBUYER2,HHTYPE,RELAT3,AGE3,SEX3,ECSTAT3,RELAT4,AGE4,SEX4,ECSTAT4,RELAT5,AGE5,SEX5,ECSTAT5,RELAT6,AGE6,SEX6,ECSTAT6,PREVTEN,PPCODENK,PPOSTC1,PPOSTC2,PREVIOUSLAKNOWN,PREVLOC,PREVLOCNAME,PREGYRHA,PREGOTHER,PREGLA,PREGGHB,PREGBLANK,BUY2LIVING,PREVTEN2,HHREGRES,HHREGRESSTILL,ARMEDFORCESSPOUSE,DISABLED,WHEEL,INC1NK,INCOME1,INC1MORT,INC2NK,INCOME2,INC2MORT,HB,SAVINGSNK,SAVINGS,PREVOWN,PREVSHARED,PROPLEN,STAIRCASE,STAIRBOUGHT,STAIROWNED,STAIRCASETOSALE,RESALE,EXDAY,EXMONTH,EXYEAR,HODAY,HOMONTH,HOYEAR,LANOMAGR,SOCTEN,FROMBEDS,FROMPROP,SOCPREVTEN,VALUE,VALUE_VALUE_CHECK,EQUITY,MORTGAGEUSED,MORTGAGE,MORTGAGELENDER,MORTGAGELENDEROTHER,MORTLEN1,EXTRABOR,DEPOSIT,CASHDIS,MRENT,HASMSCHARGE,MSCHARGE,MSCHARGE_VALUE_CHECK,DISCOUNT,GRANT
-,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,single log,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,billyboy@eyeklaud.com,,Yes - a discounted ownership scheme,Right to Acquire (RTA),,,,Yes,Yes,Yes,1,1,"1, Test Street",,Test Town,,AA1 1AA,Yes,Westminster,E09000033,1,,,,address line 1 as entered,address line 2 as entered,town or city as entered,county as entered,AB1 2CD,la as entered,2,Flat or maisonette,Purpose built,Yes,30,Non-binary,Buyer prefers not to say,17,United Kingdom,Full-time - 30 hours or more,Yes,Partner,35,Non-binary,Buyer prefers not to say,,United Kingdom,Full-time - 30 hours or more,Yes,3,Child,14,Non-binary,Child under 16,Other,Not known,Non-binary,In government training into work,Prefers not to say,Not known,Prefers not to say,Prefers not to say,,,,,Local authority tenant,Yes,SW1A,1AA,Yes,E09000033,Westminster,1,1,1,1,,Don't know,,Yes,Yes,No,Yes,Yes,Yes,13400,Yes,Yes,13400,Yes,Don’t know ,No,,Yes,No,10,,,,,,,,,,,,,,,,,110000.0,,,Yes,20000.0,Cambridge Building Society,,10,Yes,80000.0,,,Yes,100.0,,,10000.0
+,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,single log,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,billyboy@eyeklaud.com,,Yes - a discounted ownership scheme,Right to Acquire (RTA),,,,Yes,Yes,Yes,1,1,"1, Test Street",,Test Town,,AA1 1AA,Yes,Westminster,E09000033,,,Address line 1,SW1A 1AA,address line 1 as entered,address line 2 as entered,town or city as entered,county as entered,AB1 2CD,la as entered,2,Flat or maisonette,Purpose built,Yes,30,Non-binary,Buyer prefers not to say,17,United Kingdom,Full-time - 30 hours or more,Yes,Partner,35,Non-binary,Buyer prefers not to say,,United Kingdom,Full-time - 30 hours or more,Yes,3,Child,14,Non-binary,Child under 16,Other,Not known,Non-binary,In government training into work,Prefers not to say,Not known,Prefers not to say,Prefers not to say,,,,,Local authority tenant,Yes,AA1,1AA,Yes,E09000033,Westminster,1,1,1,1,,Don't know,,Yes,Yes,No,Yes,Yes,Yes,13400,Yes,Yes,13400,Yes,Don’t know ,No,,Yes,No,10,,,,,,,,,,,,,,,,,110000.0,,,Yes,20000.0,Cambridge Building Society,,10,Yes,80000.0,,,Yes,100.0,,,10000.0
diff --git a/spec/fixtures/files/sales_logs_csv_export_non_support_labels_24.csv b/spec/fixtures/files/sales_logs_csv_export_non_support_labels_24.csv
index a6eaed17a..0e9a781f5 100644
--- a/spec/fixtures/files/sales_logs_csv_export_non_support_labels_24.csv
+++ b/spec/fixtures/files/sales_logs_csv_export_non_support_labels_24.csv
@@ -1,3 +1,3 @@
Log ID,Status of log,ID of a set of duplicate logs,Time and date the log was created,Time and date the log was last updated,Year collection period opened,Was the log submitted in-service or via bulk upload?,,Is the user in the assigned_to column the data protection officer?,Day of sale completion date,Month of sale completion date,Year of sale completion date,Which organisation owned this property before the sale?,Which organisation reported the sale?,User the log is assigned to,What is the purchaser code?,Was this purchase made through an ownership scheme?,What is the type of shared ownership/discounted ownership/outright sale?,"If type = 'Other', what is the type of outright sale?",Is the buyer a company?,Will the buyer(s) live in the property?,Is this a joint purchase?,Are there more than 2 joint buyers of this property?,Did you interview the buyer to answer these questions?,Has the buyer seen the MHCLG privacy notice?,What is the UPRN of the property?,We found an address that might be this property. Is this the property address?,Address line 1 input from address matching feature,Postcode input from address matching feature,UPRN of the address selected,Address line 1,Address line 2,Town/City,County,Part 1 of the property's postcode,Part 2 of the property's postcode,LA code,LA name,How many bedrooms does the property have?,What type of unit is the property?,Which type of building is the property?,Is the property built or adapted to wheelchair-user standards?,What is buyer 1's age?,Which of these best describes buyer 1's gender identity?,What is buyer 1's ethnic group?,Which of the following best describes buyer 1's ethnic background?,What is buyer 1's nationality?,Which of these best describes buyer 1's working situation?,Will buyer 1 live in the property?,What is buyer 2 or person 2's relationship to buyer 1?,What is buyer 2 or person 2's age?,Which of these best describes buyer 2 or person 2's gender identity?,What is buyer 2's ethnic group?,Which of the following best describes buyer 2's ethnic background?,What is buyer 2's nationality?,What is buyer 2 or person 2's working situation?,Will buyer 2 live in the property?,"Besides the buyer(s), how many other people live or will live in the property?",What is person 3's relationship to buyer 1?,What is person 3's age?,What is person 3's gender identity?,What is person 3's working situation?,What is person 4's relationship to buyer 1?,What is person 4's age?,What is person 4's gender identity?,What is person 4's working situation?,What is person 5's relationship to buyer 1?,What is person 5's age?,What is person 5's gender identity?,What is person 5's working situation?,What is person 6's relationship to buyer 1?,What is person 6's age?,What is person 6's gender identity?,What is person 6's working situation?,What was buyer 1's previous tenure?,Do you know the postcode of buyer 1's last settled accommodation?,Part 1 of postcode of buyer 1's last settled accommodation,Part 2 of postcode of buyer 1's last settled accommodation,Do you know the local authority of buyer 1's last settled accommodation?,The local authority code of buyer 1's last settled accommodation,The local authority name of buyer 1's last settled accommodation,Was the buyer registered with their PRP (HA)?,Was the buyer registered with another PRP (HA)?,Was the buyer registered with the local authority?,Was the buyer registered with a Help to Buy agent?,"Populated if pregyrha, pregother, pregla and pregghb are blank","At the time of purchase, was buyer 2 living at the same address as buyer 1?",What was buyer 2's previous tenure?,Have any of the buyers ever served as a regular in the UK armed forces?,Is the buyer still serving in the UK armed forces?,Are any of the buyers a spouse or civil partner of a UK armed forces regular who died in service within the last 2 years?,Does anyone in the household consider themselves to have a disability?,Does anyone in the household use a wheelchair?,Is buyer 1's annual income known?,What is buyer 1's annual income?,Was buyer 1's income used for a mortgage application?,Is buyer 2's annual income known?,What is buyer 2's annual income?,Was buyer 2's income used for a mortgage application?,Were the buyers receiving any of these housing-related benefits immediately before buying this property?,Is the the total amount the buyers had in savings known?,What is the total amount the buyers had in savings before they paid any deposit for the property?,Have any of the buyers previously owned a property?,Was the previous property under shared ownership?,How long did the buyer(s) live in the property before purchasing it?,Is this a staircasing transaction?,What percentage of the property has been bought in this staircasing transaction?,What percentage of the property do the buyers now own in total?,Was this transaction part of a back-to-back staircasing transaction to facilitate sale of the home on the open market?,Is this a resale?,Day of the exchange of contracts,Month of the exchange of contracts,Year of the exchange of contracts,Day of the practical completion or handover date,Month of the practical completion or handover date,Year of the practical completion or handover date,Was the household rehoused under a local authority nominations agreement?,"Was the buyer a private registered provider, housing association or local authority tenant immediately before this sale?",How many bedrooms did the buyer's previous property have?,What was the previous property type?,What was the rent type of buyer's previous tenure?,What is the full purchase price?,What was the initial percentage equity stake purchased?,Was a mortgage used to buy this property?,What is the mortgage amount?,What is the name of the mortgage lender?,"If mortgagelender = 'Other', what is the name of the mortgage lender?",What is the length of the mortgage in years?,Does this include any extra borrowing?,How much was the cash deposit paid on the property?,How much cash discount was given through Social Homebuy?,What is the basic monthly rent?,Does the property have any monthly leasehold charges?,What are the total monthly leasehold charges for the property?,What was the percentage discount?,"What was the amount of any loan, grant, discount or subsidy given?"
id,status,duplicate_set_id,created_at,updated_at,collection_start_year,creation_method,bulk_upload_id,is_dpo,day,month,year,owning_organisation_name,managing_organisation_name,assigned_to,purchid,ownershipsch,type,othtype,companybuy,buylivein,jointpur,jointmore,noint,privacynotice,uprn,uprn_confirmed,address_line1_input,postcode_full_input,uprn_selection,address_line1,address_line2,town_or_city,county,pcode1,pcode2,la,la_label,beds,proptype,builtype,wchair,age1,sex1,ethnic_group,ethnic,nationality_all,ecstat1,buy1livein,relat2,age2,sex2,ethnic_group2,ethnicbuy2,nationality_all_buyer2,ecstat2,buy2livein,hholdcount,relat3,age3,sex3,ecstat3,relat4,age4,sex4,ecstat4,relat5,age5,sex5,ecstat5,relat6,age6,sex6,ecstat6,prevten,ppcodenk,ppostc1,ppostc2,previous_la_known,prevloc,prevloc_label,pregyrha,pregother,pregla,pregghb,pregblank,buy2living,prevtenbuy2,hhregres,hhregresstill,armedforcesspouse,disabled,wheel,income1nk,income1,inc1mort,income2nk,income2,inc2mort,hb,savingsnk,savings,prevown,prevshared,proplen,staircase,stairbought,stairowned,staircasesale,resale,exday,exmonth,exyear,hoday,homonth,hoyear,lanomagr,soctenant,frombeds,fromprop,socprevten,value,equity,mortgageused,mortgage,mortgagelender,mortgagelenderother,mortlen,extrabor,deposit,cashdis,mrent,has_mscharge,mscharge,discount,grant
-,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,single log,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,,Yes - a discounted ownership scheme,Right to Acquire (RTA),,,,Yes,Yes,Yes,1,1,Yes,,,1,"1, Test Street",,Test Town,,SW1A,1AA,E09000033,Westminster,2,Flat or maisonette,Purpose built,Yes,30,Non-binary,Buyer prefers not to say,17,United Kingdom,Full-time - 30 hours or more,Yes,Partner,35,Non-binary,Buyer prefers not to say,,United Kingdom,Full-time - 30 hours or more,Yes,3,Child,14,Non-binary,Child under 16,Other,Not known,Non-binary,In government training into work,Prefers not to say,Not known,Prefers not to say,Prefers not to say,,,,,Local authority tenant,Yes,SW1A,1AA,Yes,E09000033,Westminster,1,1,1,1,,Don't know,,Yes,Yes,No,Yes,Yes,Yes,13400,Yes,Yes,13400,Yes,Don’t know ,No,,Yes,No,10,,,,,,,,,,,,,,,,,110000.0,,Yes,20000.0,Cambridge Building Society,,10,Yes,80000.0,,,Yes,100.0,,10000.0
+,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,single log,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,,Yes - a discounted ownership scheme,Right to Acquire (RTA),,,,Yes,Yes,Yes,1,1,Yes,Address line 1,SW1A 1AA,,"1, Test Street",,Test Town,,AA1,1AA,E09000033,Westminster,2,Flat or maisonette,Purpose built,Yes,30,Non-binary,Buyer prefers not to say,17,United Kingdom,Full-time - 30 hours or more,Yes,Partner,35,Non-binary,Buyer prefers not to say,,United Kingdom,Full-time - 30 hours or more,Yes,3,Child,14,Non-binary,Child under 16,Other,Not known,Non-binary,In government training into work,Prefers not to say,Not known,Prefers not to say,Prefers not to say,,,,,Local authority tenant,Yes,AA1,1AA,Yes,E09000033,Westminster,1,1,1,1,,Don't know,,Yes,Yes,No,Yes,Yes,Yes,13400,Yes,Yes,13400,Yes,Don’t know ,No,,Yes,No,10,,,,,,,,,,,,,,,,,110000.0,,Yes,20000.0,Cambridge Building Society,,10,Yes,80000.0,,,Yes,100.0,,10000.0
diff --git a/spec/models/bulk_upload_spec.rb b/spec/models/bulk_upload_spec.rb
index 5195d23f4..61e16920e 100644
--- a/spec/models/bulk_upload_spec.rb
+++ b/spec/models/bulk_upload_spec.rb
@@ -24,7 +24,7 @@ RSpec.describe BulkUpload, type: :model do
let(:log) { build(:lettings_log, startdate: Time.zone.local(2025, 4, 2), bulk_upload:) }
it "has the correct number of value checks to be set as confirmed" do
- expect(bulk_upload.fields_to_confirm(log)).to match_array %w[rent_value_check void_date_value_check major_repairs_date_value_check pregnancy_value_check retirement_value_check referral_value_check net_income_value_check scharge_value_check pscharge_value_check supcharg_value_check multiple_partners_value_check partner_under_16_value_check reasonother_value_check]
+ expect(bulk_upload.fields_to_confirm(log)).to match_array %w[rent_value_check void_date_value_check major_repairs_date_value_check pregnancy_value_check retirement_value_check referral_value_check net_income_value_check scharge_value_check pscharge_value_check supcharg_value_check address_search_value_check multiple_partners_value_check partner_under_16_value_check reasonother_value_check]
end
end
@@ -32,7 +32,7 @@ RSpec.describe BulkUpload, type: :model do
let(:log) { build(:sales_log, :saledate_today, bulk_upload:) }
it "has the correct number of value checks to be set as confirmed" do
- expect(bulk_upload.fields_to_confirm(log)).to match_array %w[value_value_check monthly_charges_value_check percentage_discount_value_check income1_value_check income2_value_check combined_income_value_check retirement_value_check old_persons_shared_ownership_value_check buyer_livein_value_check student_not_child_value_check wheel_value_check mortgage_value_check savings_value_check deposit_value_check staircase_bought_value_check stairowned_value_check hodate_check shared_ownership_deposit_value_check extrabor_value_check grant_value_check discounted_sale_value_check deposit_and_mortgage_value_check multiple_partners_value_check partner_under_16_value_check]
+ expect(bulk_upload.fields_to_confirm(log)).to match_array %w[value_value_check monthly_charges_value_check percentage_discount_value_check income1_value_check income2_value_check combined_income_value_check retirement_value_check old_persons_shared_ownership_value_check buyer_livein_value_check student_not_child_value_check wheel_value_check mortgage_value_check savings_value_check deposit_value_check staircase_bought_value_check stairowned_value_check hodate_check shared_ownership_deposit_value_check extrabor_value_check grant_value_check discounted_sale_value_check deposit_and_mortgage_value_check address_search_value_check multiple_partners_value_check partner_under_16_value_check]
end
end
end
diff --git a/spec/models/form/lettings/pages/address_fallback_spec.rb b/spec/models/form/lettings/pages/address_fallback_spec.rb
index ffac6238e..d3971d540 100644
--- a/spec/models/form/lettings/pages/address_fallback_spec.rb
+++ b/spec/models/form/lettings/pages/address_fallback_spec.rb
@@ -24,6 +24,13 @@ RSpec.describe Form::Lettings::Pages::AddressFallback, type: :model do
end
it "has correct depends_on" do
- expect(page.depends_on).to eq([{ "manual_address_entry_selected" => true, "is_supported_housing?" => false }])
+ expect(page.depends_on).to eq([
+ { "is_supported_housing?" => false, "uprn_known" => nil, "uprn_selection" => "uprn_not_listed" },
+ { "is_supported_housing?" => false, "uprn_known" => 0, "uprn_selection" => "uprn_not_listed" },
+ { "is_supported_housing?" => false, "uprn_confirmed" => 0, "uprn_selection" => "uprn_not_listed" },
+ { "is_supported_housing?" => false, "uprn_known" => nil, "address_options_present?" => false },
+ { "is_supported_housing?" => false, "uprn_known" => 0, "address_options_present?" => false },
+ { "is_supported_housing?" => false, "uprn_confirmed" => 0, "address_options_present?" => false },
+ ])
end
end
diff --git a/spec/models/form/lettings/pages/address_search_spec.rb b/spec/models/form/lettings/pages/address_search_spec.rb
deleted file mode 100644
index 86c6537a1..000000000
--- a/spec/models/form/lettings/pages/address_search_spec.rb
+++ /dev/null
@@ -1,42 +0,0 @@
-require "rails_helper"
-
-RSpec.describe Form::Lettings::Pages::AddressSearch, type: :model do
- subject(:page) { described_class.new(page_id, page_definition, subsection) }
-
- let(:page_id) { nil }
- let(:page_definition) { nil }
- let(:subsection) { instance_double(Form::Subsection, form: instance_double(Form, start_date:)) }
- let(:start_date) { Time.utc(2024, 4, 1) }
-
- it "has correct subsection" do
- expect(page.subsection).to eq(subsection)
- end
-
- it "has correct questions" do
- expect(page.questions.map(&:id)).to eq(%w[uprn])
- end
-
- it "has the correct id" do
- expect(page.id).to eq("address_search")
- end
-
- it "has the correct description" do
- expect(page.description).to be_nil
- end
-
- it "has correct depends_on" do
- expect(page.depends_on).to eq([{ "is_supported_housing?" => false, "manual_address_entry_selected" => false }])
- end
-
- it "has the correct question number" do
- expect(page.question_number).to eq(12)
- end
-
- context "with 2025/26 form" do
- let(:start_date) { Time.utc(2025, 4, 1) }
-
- it "has the correct question number" do
- expect(page.question_number).to eq(16)
- end
- end
-end
diff --git a/spec/models/form/lettings/questions/address_search_spec.rb b/spec/models/form/lettings/questions/address_search_spec.rb
deleted file mode 100644
index d063a94dc..000000000
--- a/spec/models/form/lettings/questions/address_search_spec.rb
+++ /dev/null
@@ -1,68 +0,0 @@
-require "rails_helper"
-
-RSpec.describe Form::Lettings::Questions::AddressSearch, type: :model do
- subject(:question) { described_class.new(question_id, question_definition, page) }
-
- let(:question_id) { nil }
- let(:question_definition) { nil }
- let(:page) { instance_double(Form::Page, subsection: instance_double(Form::Subsection, form: instance_double(Form, start_date:))) }
- let(:start_date) { Time.utc(2024, 4, 1) }
-
- it "has correct page" do
- expect(question.page).to eq(page)
- end
-
- it "has the correct id" do
- expect(question.id).to eq("uprn")
- end
-
- it "has the correct type" do
- expect(question.type).to eq("address_search")
- end
-
- it "has the correct question number" do
- expect(question.question_number).to eq(12)
- end
-
- context "with 2025/26 form" do
- let(:start_date) { Time.utc(2025, 4, 1) }
-
- it "has the correct question number" do
- expect(question.question_number).to eq(16)
- end
- end
-
- describe "get_extra_check_answer_value" do
- context "when address is not present" do
- let(:log) { build(:lettings_log, manual_address_entry_selected: false) }
-
- it "returns nil" do
- expect(question.get_extra_check_answer_value(log)).to be_nil
- end
- end
-
- context "when address search is present" do
- let(:log) do
- build(
- :lettings_log,
- :completed,
- address_line1: "19, Charlton Gardens",
- town_or_city: "Bristol",
- postcode_full: "BS10 6LU",
- la: "E06000023",
- uprn_known: 1,
- uprn: 107,
- uprn_confirmed: 1,
- )
- end
-
- context "when uprn known" do
- it "returns formatted value" do
- expect(question.get_extra_check_answer_value(log)).to eq(
- "\n\n19, Charlton Gardens\nBristol\nBS10 6LU\nBristol, City of",
- )
- end
- end
- end
- end
-end
diff --git a/spec/models/form/lettings/questions/uprn_selection_spec.rb b/spec/models/form/lettings/questions/uprn_selection_spec.rb
index e10b22d89..c3edc646e 100644
--- a/spec/models/form/lettings/questions/uprn_selection_spec.rb
+++ b/spec/models/form/lettings/questions/uprn_selection_spec.rb
@@ -90,10 +90,9 @@ RSpec.describe Form::Lettings::Questions::UprnSelection, type: :model do
context "when the log has address line 1 input only" do
before do
- allow(address_client_instance).to receive(:result).and_return(nil)
log.address_line1_input = "Address line 1"
log.postcode_full_input = nil
- log.save!(validate: false)
+ log.save!(valudate: false)
end
it "has the correct input_playback" do
@@ -103,10 +102,9 @@ RSpec.describe Form::Lettings::Questions::UprnSelection, type: :model do
context "when the log has postcode input only" do
before do
- allow(address_client_instance).to receive(:result).and_return(nil)
log.address_line1_input = nil
log.postcode_full_input = "A1 1AA"
- log.save!(validate: false)
+ log.save!(valudate: false)
end
it "has the correct input_playback" do
@@ -118,7 +116,7 @@ RSpec.describe Form::Lettings::Questions::UprnSelection, type: :model do
before do
log.address_line1_input = "Address line 1"
log.postcode_full_input = "A1 1AA"
- log.save!(validate: false)
+ log.save!(valudate: false)
end
it "has the correct input_playback" do
diff --git a/spec/models/form/lettings/questions/uprn_spec.rb b/spec/models/form/lettings/questions/uprn_spec.rb
index 0c3ecec85..8bb932b35 100644
--- a/spec/models/form/lettings/questions/uprn_spec.rb
+++ b/spec/models/form/lettings/questions/uprn_spec.rb
@@ -52,14 +52,12 @@ RSpec.describe Form::Lettings::Questions::Uprn, type: :model do
la: "E09000003",
uprn_known:,
uprn:,
- manual_address_entry_selected:,
)
end
context "when uprn known nil" do
let(:uprn_known) { nil }
let(:uprn) { nil }
- let(:manual_address_entry_selected) { true }
it "returns formatted value" do
expect(question.get_extra_check_answer_value(log)).to be_nil
@@ -69,7 +67,6 @@ RSpec.describe Form::Lettings::Questions::Uprn, type: :model do
context "when uprn known" do
let(:uprn_known) { 1 }
let(:uprn) { 1 }
- let(:manual_address_entry_selected) { false }
it "returns formatted value" do
expect(question.get_extra_check_answer_value(log)).to eq(
@@ -81,7 +78,6 @@ RSpec.describe Form::Lettings::Questions::Uprn, type: :model do
context "when uprn not known" do
let(:uprn_known) { 0 }
let(:uprn) { nil }
- let(:manual_address_entry_selected) { true }
it "returns formatted value" do
expect(question.get_extra_check_answer_value(log)).to be_nil
diff --git a/spec/models/form/lettings/subsections/property_information_spec.rb b/spec/models/form/lettings/subsections/property_information_spec.rb
index e2b4b701a..0d3a4e99b 100644
--- a/spec/models/form/lettings/subsections/property_information_spec.rb
+++ b/spec/models/form/lettings/subsections/property_information_spec.rb
@@ -64,7 +64,11 @@ RSpec.describe Form::Lettings::Subsections::PropertyInformation, type: :model do
it "has correct pages" do
expect(property_information.pages.map(&:id)).to eq(
%w[
- address_search
+ uprn
+ uprn_confirmation
+ address_matcher
+ no_address_found
+ uprn_selection
address
property_local_authority
local_authority_rent_value_check
@@ -97,7 +101,11 @@ RSpec.describe Form::Lettings::Subsections::PropertyInformation, type: :model do
it "has correct pages" do
expect(property_information.pages.map(&:id)).to eq(
%w[
- address_search
+ uprn
+ uprn_confirmation
+ address_matcher
+ no_address_found
+ uprn_selection
address
property_local_authority
local_authority_rent_value_check
diff --git a/spec/models/form/sales/pages/address_fallback_spec.rb b/spec/models/form/sales/pages/address_fallback_spec.rb
index 35bb6cd24..4c48a46fe 100644
--- a/spec/models/form/sales/pages/address_fallback_spec.rb
+++ b/spec/models/form/sales/pages/address_fallback_spec.rb
@@ -24,6 +24,13 @@ RSpec.describe Form::Sales::Pages::AddressFallback, type: :model do
end
it "has correct depends_on" do
- expect(page.depends_on).to eq([{ "manual_address_entry_selected" => true }])
+ expect(page.depends_on).to eq([
+ { "uprn_known" => nil, "uprn_selection" => "uprn_not_listed" },
+ { "uprn_known" => 0, "uprn_selection" => "uprn_not_listed" },
+ { "uprn_confirmed" => 0, "uprn_selection" => "uprn_not_listed" },
+ { "uprn_known" => nil, "address_options_present?" => false },
+ { "uprn_known" => 0, "address_options_present?" => false },
+ { "uprn_confirmed" => 0, "address_options_present?" => false },
+ ])
end
end
diff --git a/spec/models/form/sales/pages/address_search_spec.rb b/spec/models/form/sales/pages/address_search_spec.rb
deleted file mode 100644
index 670854694..000000000
--- a/spec/models/form/sales/pages/address_search_spec.rb
+++ /dev/null
@@ -1,42 +0,0 @@
-require "rails_helper"
-
-RSpec.describe Form::Sales::Pages::AddressSearch, type: :model do
- subject(:page) { described_class.new(page_id, page_definition, subsection) }
-
- let(:page_id) { nil }
- let(:page_definition) { nil }
- let(:subsection) { instance_double(Form::Subsection, form: instance_double(Form, start_date:)) }
- let(:start_date) { Time.utc(2024, 4, 1) }
-
- it "has correct subsection" do
- expect(page.subsection).to eq(subsection)
- end
-
- it "has correct questions" do
- expect(page.questions.map(&:id)).to eq(%w[uprn])
- end
-
- it "has the correct id" do
- expect(page.id).to eq("address_search")
- end
-
- it "has the correct description" do
- expect(page.description).to be_nil
- end
-
- it "has correct depends_on" do
- expect(page.depends_on).to eq([{ "manual_address_entry_selected" => false }])
- end
-
- it "has the correct question number" do
- expect(page.question_number).to eq(15)
- end
-
- context "with 2025/26 form" do
- let(:start_date) { Time.utc(2025, 4, 1) }
-
- it "has the correct question number" do
- expect(page.question_number).to eq(13)
- end
- end
-end
diff --git a/spec/models/form/sales/pages/uprn_confirmation_spec.rb b/spec/models/form/sales/pages/uprn_confirmation_spec.rb
index 6415c2eb0..9550b9f49 100644
--- a/spec/models/form/sales/pages/uprn_confirmation_spec.rb
+++ b/spec/models/form/sales/pages/uprn_confirmation_spec.rb
@@ -7,10 +7,6 @@ RSpec.describe Form::Sales::Pages::UprnConfirmation, type: :model do
let(:page_definition) { nil }
let(:subsection) { instance_double(Form::Subsection) }
- before do
- allow(subsection).to receive(:form).and_return(instance_double(Form, start_year_2024_or_later?: false))
- end
-
it "has correct subsection" do
expect(page.subsection).to eq(subsection)
end
diff --git a/spec/models/form/sales/questions/address_search_spec.rb b/spec/models/form/sales/questions/address_search_spec.rb
deleted file mode 100644
index bb30cbfa0..000000000
--- a/spec/models/form/sales/questions/address_search_spec.rb
+++ /dev/null
@@ -1,68 +0,0 @@
-require "rails_helper"
-
-RSpec.describe Form::Sales::Questions::AddressSearch, type: :model do
- subject(:question) { described_class.new(question_id, question_definition, page) }
-
- let(:question_id) { nil }
- let(:question_definition) { nil }
- let(:page) { instance_double(Form::Page, subsection: instance_double(Form::Subsection, form: instance_double(Form, start_date:))) }
- let(:start_date) { Time.utc(2024, 4, 1) }
-
- it "has correct page" do
- expect(question.page).to eq(page)
- end
-
- it "has the correct id" do
- expect(question.id).to eq("uprn")
- end
-
- it "has the correct type" do
- expect(question.type).to eq("address_search")
- end
-
- it "has the correct question number" do
- expect(question.question_number).to eq(15)
- end
-
- context "with 2025/26 form" do
- let(:start_date) { Time.utc(2025, 4, 1) }
-
- it "has the correct question number" do
- expect(question.question_number).to eq(13)
- end
- end
-
- describe "get_extra_check_answer_value" do
- context "when address is not present" do
- let(:log) { build(:sales_log, manual_address_entry_selected: false) }
-
- it "returns nil" do
- expect(question.get_extra_check_answer_value(log)).to be_nil
- end
- end
-
- context "when address search is present" do
- let(:log) do
- build(
- :sales_log,
- :completed,
- address_line1: "19, Charlton Gardens",
- town_or_city: "Bristol",
- postcode_full: "BS10 6LU",
- la: "E06000023",
- uprn_known: 1,
- uprn: 107,
- uprn_confirmed: 1,
- )
- end
-
- context "when uprn known" do
- it "returns formatted value" do
- expect(question.get_extra_check_answer_value(log)).to eq(
- "\n\n19, Charlton Gardens\nBristol\nBS10 6LU\nBristol, City of",
- )
- end
- end
- end
- end
-end
diff --git a/spec/models/form/sales/questions/uprn_selection_spec.rb b/spec/models/form/sales/questions/uprn_selection_spec.rb
index efcf39c67..ff1b1a6dd 100644
--- a/spec/models/form/sales/questions/uprn_selection_spec.rb
+++ b/spec/models/form/sales/questions/uprn_selection_spec.rb
@@ -90,10 +90,9 @@ RSpec.describe Form::Sales::Questions::UprnSelection, type: :model do
context "when the log has address line 1 input only" do
before do
- allow(address_client_instance).to receive(:result).and_return(nil)
log.address_line1_input = "Address line 1"
log.postcode_full_input = nil
- log.save!(validate: false)
+ log.save!(valudate: false)
end
it "has the correct input_playback" do
@@ -103,10 +102,9 @@ RSpec.describe Form::Sales::Questions::UprnSelection, type: :model do
context "when the log has postcode input only" do
before do
- allow(address_client_instance).to receive(:result).and_return(nil)
log.address_line1_input = nil
log.postcode_full_input = "A1 1AA"
- log.save!(validate: false)
+ log.save!(valudate: false)
end
it "has the correct input_playback" do
@@ -118,7 +116,7 @@ RSpec.describe Form::Sales::Questions::UprnSelection, type: :model do
before do
log.address_line1_input = "Address line 1"
log.postcode_full_input = "A1 1AA"
- log.save!(validate: false)
+ log.save!(valudate: false)
end
it "has the correct input_playback" do
diff --git a/spec/models/form/sales/subsections/property_information_spec.rb b/spec/models/form/sales/subsections/property_information_spec.rb
index 7585d290a..ccfeb8e3a 100644
--- a/spec/models/form/sales/subsections/property_information_spec.rb
+++ b/spec/models/form/sales/subsections/property_information_spec.rb
@@ -55,7 +55,11 @@ RSpec.describe Form::Sales::Subsections::PropertyInformation, type: :model do
it "has correct pages" do
expect(property_information.pages.map(&:id)).to eq(
%w[
- address_search
+ uprn
+ uprn_confirmation
+ address_matcher
+ no_address_found
+ uprn_selection
address
property_local_authority
local_authority_buyer_1_income_max_value_check
@@ -85,7 +89,11 @@ RSpec.describe Form::Sales::Subsections::PropertyInformation, type: :model do
it "has correct pages" do
expect(property_information.pages.map(&:id)).to eq(
%w[
- address_search
+ uprn
+ uprn_confirmation
+ address_matcher
+ no_address_found
+ uprn_selection
address
property_local_authority
local_authority_buyer_1_income_max_value_check
diff --git a/spec/models/sales_log_spec.rb b/spec/models/sales_log_spec.rb
index 442febddb..c36884b8d 100644
--- a/spec/models/sales_log_spec.rb
+++ b/spec/models/sales_log_spec.rb
@@ -566,7 +566,6 @@ RSpec.describe SalesLog, type: :model do
ppostcode_full: nil,
prevloc: nil,
saledate: Time.zone.local(2024, 5, 2),
- manual_address_entry_selected: true,
})
end
@@ -618,7 +617,7 @@ RSpec.describe SalesLog, type: :model do
end
let(:address_sales_log_25_26) do
- create(:sales_log, :shared_ownership_setup_complete, postcode_full: "CA10 1AA", saledate: Time.zone.local(2025, 5, 2), manual_address_entry_selected: true)
+ create(:sales_log, :shared_ownership_setup_complete, postcode_full: "CA10 1AA", saledate: Time.zone.local(2025, 5, 2))
end
before do
@@ -673,11 +672,11 @@ RSpec.describe SalesLog, type: :model do
context "when saving address with LAs that have changed E-codes" do
context "when address inferred from uprn - we still get LA from postcode" do
let(:address_sales_log_24_25) do
- create(:sales_log, :shared_ownership_setup_complete, manual_address_entry_selected: false, uprn_known: 1, uprn: 1, saledate: Time.zone.local(2024, 5, 2))
+ create(:sales_log, :shared_ownership_setup_complete, uprn_known: 1, uprn: 1, saledate: Time.zone.local(2024, 5, 2))
end
let(:address_sales_log_25_26) do
- create(:sales_log, :shared_ownership_setup_complete, manual_address_entry_selected: false, uprn_known: 1, uprn: 1, saledate: Time.zone.local(2025, 5, 2))
+ create(:sales_log, :shared_ownership_setup_complete, uprn_known: 1, uprn: 1, saledate: Time.zone.local(2025, 5, 2))
end
before do
diff --git a/spec/models/validations/sales/property_validations_spec.rb b/spec/models/validations/sales/property_validations_spec.rb
index 62b65ee36..c5af3ae78 100644
--- a/spec/models/validations/sales/property_validations_spec.rb
+++ b/spec/models/validations/sales/property_validations_spec.rb
@@ -136,9 +136,9 @@ RSpec.describe Validations::Sales::PropertyValidations do
context "when within the limit and only numeric" do
let(:record) { build(:sales_log, uprn: "123456789012") }
- it "does not add an invalid UPRN error" do
+ it "does not add an error" do
property_validator.validate_uprn(record)
- expect(record.errors.added?(:uprn, I18n.t("validations.sales.property_information.uprn.invalid"))).to be false
+ expect(record.errors).not_to be_present
end
end
end
diff --git a/spec/request_helper.rb b/spec/request_helper.rb
index 2e0cc3d70..f1f208ec6 100644
--- a/spec/request_helper.rb
+++ b/spec/request_helper.rb
@@ -20,7 +20,7 @@ module RequestHelper
body = { results: [{ DPA: { UPRN: "10033558653" } }] }.to_json
WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?key&maxresults=10&minmatch=0.4&query=Address%20line%201,%20SW1A%201AA")
.to_return(status: 200, body:, headers: {})
- body = { results: [{ DPA: { "POSTCODE": "SW1A 1AA", "POST_TOWN": "London", "PO_BOX_NUMBER": "The Mall, City Of Westminster" } }] }.to_json
+ body = { results: [{ DPA: { "POSTCODE": "SW1A 1AA", "POST_TOWN": "London" } }] }.to_json
WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/uprn?dataset=DPA,LPI&key&uprn=1")
.to_return(status: 200, body:, headers: {})
WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/uprn?dataset=DPA,LPI&key&uprn=10033558653")
diff --git a/spec/requests/address_search_controller_spec.rb b/spec/requests/address_search_controller_spec.rb
deleted file mode 100644
index 5c2acd11a..000000000
--- a/spec/requests/address_search_controller_spec.rb
+++ /dev/null
@@ -1,148 +0,0 @@
-require "rails_helper"
-
-RSpec.describe AddressSearchController, type: :request do
- let(:user) { create(:user) }
-
- before do
- sign_in user
- end
-
- describe "#manual input" do
- context "when no address data is given and user chooses to enter address manually" do
- let(:sales_log) { create(:sales_log, :shared_ownership_setup_complete, manual_address_entry_selected: false, assigned_to: user) }
-
- it "correctly sets address fields" do
- sales_log.reload
- expect(sales_log.manual_address_entry_selected).to eq(false)
- expect(sales_log.uprn_known).to eq(nil)
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(nil)
- expect(sales_log.postcode_full).to eq(nil)
- expect(sales_log.address_line1).to eq(nil)
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.la).to eq(nil)
-
- get "/address-search/manual-input/sales_log/#{sales_log.id}"
-
- sales_log.reload
- expect(sales_log.manual_address_entry_selected).to eq(true)
- expect(sales_log.uprn_known).to eq(0)
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(nil)
- expect(sales_log.postcode_full).to eq(nil)
- expect(sales_log.address_line1).to eq(nil)
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.la).to eq(nil)
- end
- end
-
- context "when choosing to manually input an address for a log that has an address searched value" do
- let(:lettings_log) { create(:lettings_log, :completed, manual_address_entry_selected: false, assigned_to: user) }
-
- it "correctly sets address fields" do
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(1)
- expect(lettings_log.uprn).to eq("10033558653")
- expect(lettings_log.uprn_confirmed).to eq(1)
- expect(lettings_log.uprn_selection).to eq("10033558653")
- expect(lettings_log.postcode_known).to eq(1)
- expect(lettings_log.postcode_full).to eq("SW1A 1AA")
- expect(lettings_log.address_line1).to eq("The Mall, City Of Westminster")
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq("London")
- expect(lettings_log.la).to eq("E09000033")
-
- get "/address-search/manual-input/lettings_log/#{lettings_log.id}"
-
- lettings_log.reload
- expect(lettings_log.manual_address_entry_selected).to eq(true)
- expect(lettings_log.uprn_known).to eq(0)
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(nil)
- expect(lettings_log.postcode_full).to eq(nil)
- expect(lettings_log.address_line1).to eq(nil)
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.la).to eq(nil)
- end
- end
- end
-
- describe "#search input" do
- context "when no address is entered manually and choosing to search instead" do
- let(:lettings_log) { create(:lettings_log, :setup_completed, manual_address_entry_selected: true, assigned_to: user) }
-
- it "correctly sets address fields" do
- lettings_log.reload
- expect(lettings_log.manual_address_entry_selected).to eq(true)
- expect(lettings_log.uprn_known).to eq(0)
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(nil)
- expect(lettings_log.postcode_full).to eq(nil)
- expect(lettings_log.address_line1).to eq(nil)
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.la).to eq(nil)
-
- get "/address-search/search-input/lettings_log/#{lettings_log.id}"
-
- lettings_log.reload
- expect(lettings_log.manual_address_entry_selected).to eq(false)
- expect(lettings_log.uprn_known).to eq(nil)
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(nil)
- expect(lettings_log.postcode_full).to eq(nil)
- expect(lettings_log.address_line1).to eq(nil)
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.la).to eq(nil)
- end
- end
-
- context "when choosing to search for an address for a log that has an address searched value" do
- let(:sales_log) { create(:sales_log, :completed, manual_address_entry_selected: true, town_or_city: "Test Town", assigned_to: user) }
-
- it "correctly sets address fields" do
- sales_log.reload
- expect(sales_log.manual_address_entry_selected).to eq(true)
- expect(sales_log.uprn_known).to eq(0)
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(0)
- expect(sales_log.postcode_full).to eq("SW1A 1AA")
- expect(sales_log.address_line1).to eq("Address line 1")
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq("Test Town")
- expect(sales_log.la).to eq("E09000033")
-
- get "/address-search/search-input/sales_log/#{sales_log.id}"
-
- sales_log.reload
- expect(sales_log.manual_address_entry_selected).to eq(false)
- expect(sales_log.uprn_known).to eq(nil)
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(nil)
- expect(sales_log.postcode_full).to eq(nil)
- expect(sales_log.address_line1).to eq(nil)
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.la).to eq(nil)
- end
- end
- end
-end
diff --git a/spec/requests/duplicate_logs_controller_spec.rb b/spec/requests/duplicate_logs_controller_spec.rb
index c2c05e748..700964fcf 100644
--- a/spec/requests/duplicate_logs_controller_spec.rb
+++ b/spec/requests/duplicate_logs_controller_spec.rb
@@ -77,8 +77,8 @@ RSpec.describe DuplicateLogsController, type: :request do
end
it "displays check your answers for each log with correct questions where UPRN is given" do
- lettings_log.update!(uprn: "123", uprn_known: 1, uprn_confirmed: 1, manual_address_entry_selected: false)
- duplicate_logs[0].update!(uprn: "123", uprn_known: 1, uprn_confirmed: 1, manual_address_entry_selected: false)
+ lettings_log.update!(uprn: "123", uprn_known: 1, uprn_confirmed: 1)
+ duplicate_logs[0].update!(uprn: "123", uprn_known: 1, uprn_confirmed: 1)
get "/lettings-logs/#{lettings_log.id}/duplicate-logs?original_log_id=#{lettings_log.id}"
expect(page).to have_content("Q5 - Tenancy start date", count: 3)
@@ -186,9 +186,9 @@ RSpec.describe DuplicateLogsController, type: :request do
end
it "displays check your answers for each log with correct questions when UPRN is given" do
- sales_log.update!(uprn: "123", uprn_known: 1, manual_address_entry_selected: false)
- duplicate_logs[0].update!(uprn: "123", uprn_known: 1, manual_address_entry_selected: false)
- duplicate_logs[1].update!(uprn: "123", uprn_known: 1, manual_address_entry_selected: false)
+ sales_log.update!(uprn: "123", uprn_known: 1)
+ duplicate_logs[0].update!(uprn: "123", uprn_known: 1)
+ duplicate_logs[1].update!(uprn: "123", uprn_known: 1)
get "/sales-logs/#{sales_log.id}/duplicate-logs?original_log_id=#{sales_log.id}"
expect(page).to have_content("Q1 - Sale completion date", count: 3)
diff --git a/spec/services/csv/sales_log_csv_service_spec.rb b/spec/services/csv/sales_log_csv_service_spec.rb
index 5e041b2d5..3cf56af2e 100644
--- a/spec/services/csv/sales_log_csv_service_spec.rb
+++ b/spec/services/csv/sales_log_csv_service_spec.rb
@@ -199,7 +199,7 @@ RSpec.describe Csv::SalesLogCsvService do
let(:fixed_time) { Time.zone.local(2024, 5, 1) }
before do
- log.update!(nationality_all: 36, manual_address_entry_selected: false, uprn: "1", uprn_known: 1)
+ log.update!(nationality_all: 36)
end
it "exports the CSV with the 2024 ordering and all values correct" do
@@ -286,10 +286,6 @@ RSpec.describe Csv::SalesLogCsvService do
let(:fixed_time) { Time.zone.local(2024, 5, 1) }
let(:year) { 2024 }
- before do
- log.update!(manual_address_entry_selected: false, uprn: "1", uprn_known: 1)
- end
-
it "exports the CSV with all values correct" do
expected_content = CSV.read("spec/fixtures/files/sales_logs_csv_export_codes_24.csv")
values_to_delete = %w[ID]
@@ -342,7 +338,7 @@ RSpec.describe Csv::SalesLogCsvService do
let(:fixed_time) { Time.zone.local(2024, 5, 1) }
before do
- log.update!(nationality_all: 36, manual_address_entry_selected: false, uprn: "1", uprn_known: 1)
+ log.update!(nationality_all: 36)
end
context "and exporting with labels" do
diff --git a/spec/services/exports/lettings_log_export_service_spec.rb b/spec/services/exports/lettings_log_export_service_spec.rb
index 12e3809f0..1db9cf4d9 100644
--- a/spec/services/exports/lettings_log_export_service_spec.rb
+++ b/spec/services/exports/lettings_log_export_service_spec.rb
@@ -431,7 +431,7 @@ RSpec.describe Exports::LettingsLogExportService do
end
context "and one lettings log is available for export" do
- let!(:lettings_log) { FactoryBot.create(:lettings_log, :completed, assigned_to: user, age1: 35, sex1: "F", age2: 32, sex2: "M", ppostcode_full: "A1 1AA", nationality_all_group: 13, propcode: "123", postcode_full: "SE2 6RT", tenancycode: "BZ737", startdate: Time.zone.local(2024, 4, 2, 10, 36, 49), voiddate: Time.zone.local(2021, 11, 3), mrcdate: Time.zone.local(2022, 5, 5, 10, 36, 49), tenancylength: 5, underoccupation_benefitcap: 4, creation_method: 2, bulk_upload_id: 1, address_line1_as_entered: "address line 1 as entered", address_line2_as_entered: "address line 2 as entered", town_or_city_as_entered: "town or city as entered", county_as_entered: "county as entered", postcode_full_as_entered: "AB1 2CD", la_as_entered: "la as entered", manual_address_entry_selected: false, uprn: "1", uprn_known: 1) }
+ let!(:lettings_log) { FactoryBot.create(:lettings_log, :completed, assigned_to: user, age1: 35, sex1: "F", age2: 32, sex2: "M", ppostcode_full: "A1 1AA", nationality_all_group: 13, propcode: "123", postcode_full: "SE2 6RT", tenancycode: "BZ737", startdate: Time.zone.local(2024, 4, 2, 10, 36, 49), voiddate: Time.zone.local(2021, 11, 3), mrcdate: Time.zone.local(2022, 5, 5, 10, 36, 49), tenancylength: 5, underoccupation_benefitcap: 4, creation_method: 2, bulk_upload_id: 1, address_line1_as_entered: "address line 1 as entered", address_line2_as_entered: "address line 2 as entered", town_or_city_as_entered: "town or city as entered", county_as_entered: "county as entered", postcode_full_as_entered: "AB1 2CD", la_as_entered: "la as entered") }
let(:expected_zip_filename) { "core_2024_2025_apr_mar_f0001_inc0001.zip" }
let(:expected_data_filename) { "core_2024_2025_apr_mar_f0001_inc0001_pt001.xml" }
let(:xml_export_file) { File.open("spec/fixtures/exports/general_needs_log_24_25.xml", "r:UTF-8") }
diff --git a/spec/shared/shared_examples_for_derived_fields.rb b/spec/shared/shared_examples_for_derived_fields.rb
index 3f746468a..3e6b685df 100644
--- a/spec/shared/shared_examples_for_derived_fields.rb
+++ b/spec/shared/shared_examples_for_derived_fields.rb
@@ -25,14 +25,11 @@ RSpec.shared_examples "shared examples for derived fields" do |log_type|
end
it "does not affect older logs with uprn_confirmed == 0" do
- Timecop.freeze(Time.zone.local(2023, 4, 1)) do
- log = FactoryBot.build(log_type, uprn_known: 0, uprn: nil, uprn_confirmed: 0)
- allow(log.form).to receive(:start_year_2024_or_later?).and_return(false)
- expect { log.set_derived_fields! }.to not_change(log, :uprn_known)
- .and not_change(log, :uprn)
- .and not_change(log, :uprn_confirmed)
- end
- Timecop.return
+ log = FactoryBot.build(log_type, uprn_known: 0, uprn: nil, uprn_confirmed: 0)
+
+ expect { log.set_derived_fields! }.to not_change(log, :uprn_known)
+ .and not_change(log, :uprn)
+ .and not_change(log, :uprn_confirmed)
end
end
end
diff --git a/spec/shared/shared_log_examples.rb b/spec/shared/shared_log_examples.rb
index 77be654d7..ef9ba32e6 100644
--- a/spec/shared/shared_log_examples.rb
+++ b/spec/shared/shared_log_examples.rb
@@ -81,6 +81,7 @@ RSpec.shared_examples "shared log examples" do |log_type|
expect { log.process_uprn_change! }.to change(log, :address_line1).from(nil).to("0, Building Name, Thoroughfare")
.and change(log, :town_or_city).from(nil).to("Posttown")
.and change(log, :postcode_full).from(nil).to("POSTCODE")
+ .and change(log, :uprn_confirmed).from(1).to(nil)
.and change(log, :county).from("county").to(nil)
end
end
@@ -155,6 +156,7 @@ RSpec.shared_examples "shared log examples" do |log_type|
.and change(log, :uprn_confirmed).from(nil).to(1)
.and change(log, :uprn).from(nil).to("UPRN")
.and change(log, :uprn_known).from(nil).to(1)
+ .and change(log, :uprn_selection).from("UPRN").to(nil)
.and change(log, :county).from("county").to(nil)
end
end
From f39b2a9c352b01986e73dbfc52171870c514ce28 Mon Sep 17 00:00:00 2001
From: kosiakkatrina <54268893+kosiakkatrina@users.noreply.github.com>
Date: Tue, 4 Mar 2025 14:10:28 +0000
Subject: [PATCH 3/6] CLDC-3861 Move first let/new build questions (#2956)
* Move new build questions
* Remove check_answers_card_number for property information
---
.../form/lettings/pages/rent_value_check.rb | 5 ++---
app/models/form/lettings/questions/beds.rb | 1 -
.../form/lettings/questions/builtype.rb | 1 -
...rst_time_property_let_as_social_housing.rb | 1 -
.../major_repairs_date_value_check.rb | 1 -
.../form/lettings/questions/majorrepairs.rb | 1 -
app/models/form/lettings/questions/mrcdate.rb | 1 -
.../lettings/questions/previous_let_type.rb | 1 -
.../lettings/questions/rent_value_check.rb | 5 ++---
app/models/form/lettings/questions/rsnvac.rb | 1 -
.../lettings/questions/rsnvac_first_let.rb | 1 -
.../form/lettings/questions/sheltered.rb | 1 -
.../form/lettings/questions/unittype_gn.rb | 1 -
.../questions/void_date_value_check.rb | 1 -
.../form/lettings/questions/voiddate.rb | 1 -
.../form/lettings/questions/wheelchair.rb | 1 -
.../subsections/income_and_benefits.rb | 2 +-
.../subsections/property_information.rb | 19 +++++++++++++------
.../form/lettings/questions/rsnvac_spec.rb | 4 ----
.../form/lettings/questions/voiddate_spec.rb | 4 ----
.../subsections/property_information_spec.rb | 8 ++++----
21 files changed, 22 insertions(+), 39 deletions(-)
diff --git a/app/models/form/lettings/pages/rent_value_check.rb b/app/models/form/lettings/pages/rent_value_check.rb
index 5a1ecc847..314883fda 100644
--- a/app/models/form/lettings/pages/rent_value_check.rb
+++ b/app/models/form/lettings/pages/rent_value_check.rb
@@ -1,5 +1,5 @@
class Form::Lettings::Pages::RentValueCheck < ::Form::Page
- def initialize(id, hsh, subsection, check_answers_card_number: nil)
+ def initialize(id, hsh, subsection)
super(id, hsh, subsection)
@depends_on = [{ "rent_soft_validation_triggered?" => true }]
@copy_key = "lettings.soft_validations.rent_value_check"
@@ -23,11 +23,10 @@ class Form::Lettings::Pages::RentValueCheck < ::Form::Page
},
],
}
- @check_answers_card_number = check_answers_card_number
end
def questions
- @questions ||= [Form::Lettings::Questions::RentValueCheck.new(nil, nil, self, check_answers_card_number: @check_answers_card_number)]
+ @questions ||= [Form::Lettings::Questions::RentValueCheck.new(nil, nil, self)]
end
def interruption_screen_question_ids
diff --git a/app/models/form/lettings/questions/beds.rb b/app/models/form/lettings/questions/beds.rb
index 4661f5367..1bafa3ddf 100644
--- a/app/models/form/lettings/questions/beds.rb
+++ b/app/models/form/lettings/questions/beds.rb
@@ -4,7 +4,6 @@ class Form::Lettings::Questions::Beds < ::Form::Question
@id = "beds"
@type = "numeric"
@width = 2
- @check_answers_card_number = 0
@max = 12
@min = 1
@step = 1
diff --git a/app/models/form/lettings/questions/builtype.rb b/app/models/form/lettings/questions/builtype.rb
index 7df3c46dd..8c34beca1 100644
--- a/app/models/form/lettings/questions/builtype.rb
+++ b/app/models/form/lettings/questions/builtype.rb
@@ -3,7 +3,6 @@ class Form::Lettings::Questions::Builtype < ::Form::Question
super
@id = "builtype"
@type = "radio"
- @check_answers_card_number = 0
@answer_options = ANSWER_OPTIONS
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/questions/first_time_property_let_as_social_housing.rb b/app/models/form/lettings/questions/first_time_property_let_as_social_housing.rb
index 0f737fa6e..09e6ece30 100644
--- a/app/models/form/lettings/questions/first_time_property_let_as_social_housing.rb
+++ b/app/models/form/lettings/questions/first_time_property_let_as_social_housing.rb
@@ -3,7 +3,6 @@ class Form::Lettings::Questions::FirstTimePropertyLetAsSocialHousing < ::Form::Q
super
@id = "first_time_property_let_as_social_housing"
@type = "radio"
- @check_answers_card_number = 0
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/questions/major_repairs_date_value_check.rb b/app/models/form/lettings/questions/major_repairs_date_value_check.rb
index 0e9cb4171..dd27bda58 100644
--- a/app/models/form/lettings/questions/major_repairs_date_value_check.rb
+++ b/app/models/form/lettings/questions/major_repairs_date_value_check.rb
@@ -4,7 +4,6 @@ class Form::Lettings::Questions::MajorRepairsDateValueCheck < ::Form::Question
@id = "major_repairs_date_value_check"
@copy_key = "lettings.soft_validations.major_repairs_date_value_check"
@type = "interruption_screen"
- @check_answers_card_number = 0
@answer_options = ANSWER_OPTIONS
@hidden_in_check_answers = {
"depends_on" => [
diff --git a/app/models/form/lettings/questions/majorrepairs.rb b/app/models/form/lettings/questions/majorrepairs.rb
index ef33c1e01..a0c8a3a5c 100644
--- a/app/models/form/lettings/questions/majorrepairs.rb
+++ b/app/models/form/lettings/questions/majorrepairs.rb
@@ -4,7 +4,6 @@ class Form::Lettings::Questions::Majorrepairs < ::Form::Question
@id = "majorrepairs"
@copy_key = "lettings.property_information.property_major_repairs.majorrepairs"
@type = "radio"
- @check_answers_card_number = 0
@answer_options = ANSWER_OPTIONS
@conditional_for = { "mrcdate" => [1] }
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
diff --git a/app/models/form/lettings/questions/mrcdate.rb b/app/models/form/lettings/questions/mrcdate.rb
index 33c8f2c5f..0c311d186 100644
--- a/app/models/form/lettings/questions/mrcdate.rb
+++ b/app/models/form/lettings/questions/mrcdate.rb
@@ -4,7 +4,6 @@ class Form::Lettings::Questions::Mrcdate < ::Form::Question
@id = "mrcdate"
@copy_key = "lettings.property_information.property_major_repairs.mrcdate"
@type = "date"
- @check_answers_card_number = 0
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/questions/previous_let_type.rb b/app/models/form/lettings/questions/previous_let_type.rb
index 8270d621c..a3b038d6d 100644
--- a/app/models/form/lettings/questions/previous_let_type.rb
+++ b/app/models/form/lettings/questions/previous_let_type.rb
@@ -3,7 +3,6 @@ class Form::Lettings::Questions::PreviousLetType < ::Form::Question
super
@id = "unitletas"
@type = "radio"
- @check_answers_card_number = 0
@answer_options = answer_options
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/questions/rent_value_check.rb b/app/models/form/lettings/questions/rent_value_check.rb
index fb7ac8d16..41e8c9fb8 100644
--- a/app/models/form/lettings/questions/rent_value_check.rb
+++ b/app/models/form/lettings/questions/rent_value_check.rb
@@ -1,10 +1,9 @@
class Form::Lettings::Questions::RentValueCheck < ::Form::Question
- def initialize(id, hsh, page, check_answers_card_number:)
- super(id, hsh, page)
+ def initialize(id, hsh, page)
+ super
@id = "rent_value_check"
@copy_key = "lettings.soft_validations.rent_value_check"
@type = "interruption_screen"
- @check_answers_card_number = check_answers_card_number
@answer_options = ANSWER_OPTIONS
@hidden_in_check_answers = { "depends_on" => [{ "rent_value_check" => 0 }, { "rent_value_check" => 1 }] }
end
diff --git a/app/models/form/lettings/questions/rsnvac.rb b/app/models/form/lettings/questions/rsnvac.rb
index 377641c94..42c8d9f92 100644
--- a/app/models/form/lettings/questions/rsnvac.rb
+++ b/app/models/form/lettings/questions/rsnvac.rb
@@ -3,7 +3,6 @@ class Form::Lettings::Questions::Rsnvac < ::Form::Question
super
@id = "rsnvac"
@type = "radio"
- @check_answers_card_number = 0
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/questions/rsnvac_first_let.rb b/app/models/form/lettings/questions/rsnvac_first_let.rb
index 27c43896d..01389871c 100644
--- a/app/models/form/lettings/questions/rsnvac_first_let.rb
+++ b/app/models/form/lettings/questions/rsnvac_first_let.rb
@@ -3,7 +3,6 @@ class Form::Lettings::Questions::RsnvacFirstLet < ::Form::Question
super
@id = "rsnvac"
@type = "radio"
- @check_answers_card_number = 0
@answer_options = ANSWER_OPTIONS
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/questions/sheltered.rb b/app/models/form/lettings/questions/sheltered.rb
index 4c0ec4c07..35a16ae05 100644
--- a/app/models/form/lettings/questions/sheltered.rb
+++ b/app/models/form/lettings/questions/sheltered.rb
@@ -3,7 +3,6 @@ class Form::Lettings::Questions::Sheltered < ::Form::Question
super
@id = "sheltered"
@type = "radio"
- @check_answers_card_number = 0
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/questions/unittype_gn.rb b/app/models/form/lettings/questions/unittype_gn.rb
index 95a199b98..ad8298929 100644
--- a/app/models/form/lettings/questions/unittype_gn.rb
+++ b/app/models/form/lettings/questions/unittype_gn.rb
@@ -3,7 +3,6 @@ class Form::Lettings::Questions::UnittypeGn < ::Form::Question
super
@id = "unittype_gn"
@type = "radio"
- @check_answers_card_number = 0
@answer_options = ANSWER_OPTIONS
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/questions/void_date_value_check.rb b/app/models/form/lettings/questions/void_date_value_check.rb
index faf507a1b..dc1e26809 100644
--- a/app/models/form/lettings/questions/void_date_value_check.rb
+++ b/app/models/form/lettings/questions/void_date_value_check.rb
@@ -4,7 +4,6 @@ class Form::Lettings::Questions::VoidDateValueCheck < ::Form::Question
@id = "void_date_value_check"
@copy_key = "lettings.soft_validations.void_date_value_check"
@type = "interruption_screen"
- @check_answers_card_number = 0
@answer_options = ANSWER_OPTIONS
@hidden_in_check_answers = { "depends_on" => [{ "void_date_value_check" => 0 }, { "void_date_value_check" => 1 }] }
end
diff --git a/app/models/form/lettings/questions/voiddate.rb b/app/models/form/lettings/questions/voiddate.rb
index 1f5d2317a..3bce8a7b8 100644
--- a/app/models/form/lettings/questions/voiddate.rb
+++ b/app/models/form/lettings/questions/voiddate.rb
@@ -3,7 +3,6 @@ class Form::Lettings::Questions::Voiddate < ::Form::Question
super
@id = "voiddate"
@type = "date"
- @check_answers_card_number = 0
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
@top_guidance_partial = "void_date"
end
diff --git a/app/models/form/lettings/questions/wheelchair.rb b/app/models/form/lettings/questions/wheelchair.rb
index f766a0e44..9da5399e6 100644
--- a/app/models/form/lettings/questions/wheelchair.rb
+++ b/app/models/form/lettings/questions/wheelchair.rb
@@ -3,7 +3,6 @@ class Form::Lettings::Questions::Wheelchair < ::Form::Question
super
@id = "wchair"
@type = "radio"
- @check_answers_card_number = 0
@answer_options = ANSWER_OPTIONS
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/subsections/income_and_benefits.rb b/app/models/form/lettings/subsections/income_and_benefits.rb
index 4ad3003cb..e037dfc2a 100644
--- a/app/models/form/lettings/subsections/income_and_benefits.rb
+++ b/app/models/form/lettings/subsections/income_and_benefits.rb
@@ -20,7 +20,7 @@ class Form::Lettings::Subsections::IncomeAndBenefits < ::Form::Subsection
Form::Lettings::Pages::RentBiWeekly.new(nil, nil, self),
Form::Lettings::Pages::Rent4Weekly.new(nil, nil, self),
Form::Lettings::Pages::RentMonthly.new(nil, nil, self),
- Form::Lettings::Pages::RentValueCheck.new("brent_rent_value_check", nil, self, check_answers_card_number: 0),
+ Form::Lettings::Pages::RentValueCheck.new("brent_rent_value_check", nil, self),
Form::Lettings::Pages::SchargeValueCheck.new(nil, nil, self),
Form::Lettings::Pages::PschargeValueCheck.new(nil, nil, self),
Form::Lettings::Pages::SupchargValueCheck.new(nil, nil, self),
diff --git a/app/models/form/lettings/subsections/property_information.rb b/app/models/form/lettings/subsections/property_information.rb
index 4d3e022c0..d5005b142 100644
--- a/app/models/form/lettings/subsections/property_information.rb
+++ b/app/models/form/lettings/subsections/property_information.rb
@@ -8,19 +8,17 @@ class Form::Lettings::Subsections::PropertyInformation < ::Form::Subsection
def pages
@pages ||= [
+ (first_let_questions if form.start_year_2025_or_later?),
uprn_questions,
Form::Lettings::Pages::PropertyLocalAuthority.new(nil, nil, self),
- Form::Lettings::Pages::RentValueCheck.new("local_authority_rent_value_check", nil, self, check_answers_card_number: nil),
- Form::Lettings::Pages::FirstTimePropertyLetAsSocialHousing.new(nil, nil, self),
- Form::Lettings::Pages::PropertyLetType.new(nil, nil, self),
- Form::Lettings::Pages::PropertyVacancyReasonNotFirstLet.new(nil, nil, self),
- Form::Lettings::Pages::PropertyVacancyReasonFirstLet.new(nil, nil, self),
+ Form::Lettings::Pages::RentValueCheck.new("local_authority_rent_value_check", nil, self),
+ (first_let_questions unless form.start_year_2025_or_later?),
number_of_times_relet,
Form::Lettings::Pages::PropertyUnitType.new(nil, nil, self),
Form::Lettings::Pages::PropertyBuildingType.new(nil, nil, self),
Form::Lettings::Pages::PropertyWheelchairAccessible.new(nil, nil, self),
Form::Lettings::Pages::PropertyNumberOfBedrooms.new(nil, nil, self),
- Form::Lettings::Pages::RentValueCheck.new("beds_rent_value_check", nil, self, check_answers_card_number: 0),
+ Form::Lettings::Pages::RentValueCheck.new("beds_rent_value_check", nil, self),
Form::Lettings::Pages::VoidDate.new(nil, nil, self),
Form::Lettings::Pages::VoidDateValueCheck.new(nil, nil, self),
Form::Lettings::Pages::PropertyMajorRepairs.new(nil, nil, self),
@@ -52,6 +50,15 @@ class Form::Lettings::Subsections::PropertyInformation < ::Form::Subsection
Form::Lettings::Pages::PropertyNumberOfTimesRelet.new(nil, nil, self) unless form.start_year_2024_or_later?
end
+ def first_let_questions
+ [
+ Form::Lettings::Pages::FirstTimePropertyLetAsSocialHousing.new(nil, nil, self),
+ Form::Lettings::Pages::PropertyLetType.new(nil, nil, self),
+ Form::Lettings::Pages::PropertyVacancyReasonNotFirstLet.new(nil, nil, self),
+ Form::Lettings::Pages::PropertyVacancyReasonFirstLet.new(nil, nil, self),
+ ]
+ end
+
def displayed_in_tasklist?(log)
!(log.is_supported_housing? && log.is_renewal?)
end
diff --git a/spec/models/form/lettings/questions/rsnvac_spec.rb b/spec/models/form/lettings/questions/rsnvac_spec.rb
index 6d4145f95..9a63f1b23 100644
--- a/spec/models/form/lettings/questions/rsnvac_spec.rb
+++ b/spec/models/form/lettings/questions/rsnvac_spec.rb
@@ -76,10 +76,6 @@ RSpec.describe Form::Lettings::Questions::Rsnvac, type: :model do
end
end
- it "has the correct check_answers_card_number" do
- expect(question.check_answers_card_number).to eq(0)
- end
-
context "with 2024/25 form" do
let(:form) { instance_double(Form, start_date: Time.zone.local(2024, 4, 1)) }
diff --git a/spec/models/form/lettings/questions/voiddate_spec.rb b/spec/models/form/lettings/questions/voiddate_spec.rb
index 639501c42..730e3da4b 100644
--- a/spec/models/form/lettings/questions/voiddate_spec.rb
+++ b/spec/models/form/lettings/questions/voiddate_spec.rb
@@ -15,10 +15,6 @@ RSpec.describe Form::Lettings::Questions::Voiddate, type: :model do
expect(question.id).to eq("voiddate")
end
- it "has the correct check_answers_card_number" do
- expect(question.check_answers_card_number).to eq(0)
- end
-
it "has the correct question_number" do
expect(question.question_number).to eq(23)
end
diff --git a/spec/models/form/lettings/subsections/property_information_spec.rb b/spec/models/form/lettings/subsections/property_information_spec.rb
index 0d3a4e99b..e0e9a61ae 100644
--- a/spec/models/form/lettings/subsections/property_information_spec.rb
+++ b/spec/models/form/lettings/subsections/property_information_spec.rb
@@ -101,6 +101,10 @@ RSpec.describe Form::Lettings::Subsections::PropertyInformation, type: :model do
it "has correct pages" do
expect(property_information.pages.map(&:id)).to eq(
%w[
+ first_time_property_let_as_social_housing
+ property_let_type
+ property_vacancy_reason_not_first_let
+ property_vacancy_reason_first_let
uprn
uprn_confirmation
address_matcher
@@ -109,10 +113,6 @@ RSpec.describe Form::Lettings::Subsections::PropertyInformation, type: :model do
address
property_local_authority
local_authority_rent_value_check
- first_time_property_let_as_social_housing
- property_let_type
- property_vacancy_reason_not_first_let
- property_vacancy_reason_first_let
property_unit_type
property_building_type
property_wheelchair_accessible
From 72a94810eb0be8ffaf8bb103c387a4a81c87fb0f Mon Sep 17 00:00:00 2001
From: Manny Dinssa <44172848+Dinssa@users.noreply.github.com>
Date: Tue, 4 Mar 2025 14:48:50 +0000
Subject: [PATCH 4/6] CLDC-3843: Lettings household situation change Q84
question format (#2958)
* Rename old renewal prp page and question
* Update subsection
* Add referral_type to lettings logs
* Add two-step source of referral for letting questions
* Update test
* Update validations
* Update tests with referral_type
* Fix test
* Update test
* Update referral type
* Update factory bot
* Remove hint text
* Change check answer label
* Update incorrect value
* Rename old referral pages and questions
* Update referral type options
* Remove clearing
* Update id name
* Update row parser for referral type
* Update test
---
.../lettings_log_variables.rb | 3 +
.../form/lettings/pages/referral_direct.rb | 11 ++
...{referral.rb => referral_general_needs.rb} | 4 +-
.../pages/referral_general_needs_prp.rb | 12 ++
.../form/lettings/pages/referral_hsc.rb | 11 ++
.../form/lettings/pages/referral_justice.rb | 11 ++
app/models/form/lettings/pages/referral_la.rb | 11 ++
.../form/lettings/pages/referral_prp.rb | 3 +-
.../form/lettings/pages/referral_type.rb | 10 ++
.../lettings/questions/referral_direct.rb | 26 +++++
...{referral.rb => referral_general_needs.rb} | 2 +-
.../questions/referral_general_needs_prp.rb | 105 ++++++++++++++++++
.../form/lettings/questions/referral_hsc.rb | 32 ++++++
.../lettings/questions/referral_justice.rb | 23 ++++
.../form/lettings/questions/referral_la.rb | 29 +++++
.../form/lettings/questions/referral_prp.rb | 105 +++---------------
.../form/lettings/questions/referral_type.rb | 38 +++++++
.../subsections/household_situation.rb | 27 ++++-
.../validations/household_validations.rb | 3 +
.../validations/property_validations.rb | 1 +
.../lettings/year2025/row_parser.rb | 20 ++++
.../2025/lettings/household_situation.en.yml | 62 ++++++-----
...0643_add_referral_type_to_lettings_logs.rb | 5 +
db/schema.rb | 4 +-
spec/factories/lettings_log.rb | 1 +
....rb => referral_general_needs_prp_spec.rb} | 2 +-
...spec.rb => referral_general_needs_spec.rb} | 2 +-
.../subsections/household_situation_spec.rb | 38 ++++++-
.../validations/household_validations_spec.rb | 25 +++++
.../validations/property_validations_spec.rb | 1 +
30 files changed, 495 insertions(+), 132 deletions(-)
create mode 100644 app/models/form/lettings/pages/referral_direct.rb
rename app/models/form/lettings/pages/{referral.rb => referral_general_needs.rb} (64%)
create mode 100644 app/models/form/lettings/pages/referral_general_needs_prp.rb
create mode 100644 app/models/form/lettings/pages/referral_hsc.rb
create mode 100644 app/models/form/lettings/pages/referral_justice.rb
create mode 100644 app/models/form/lettings/pages/referral_la.rb
create mode 100644 app/models/form/lettings/pages/referral_type.rb
create mode 100644 app/models/form/lettings/questions/referral_direct.rb
rename app/models/form/lettings/questions/{referral.rb => referral_general_needs.rb} (97%)
create mode 100644 app/models/form/lettings/questions/referral_general_needs_prp.rb
create mode 100644 app/models/form/lettings/questions/referral_hsc.rb
create mode 100644 app/models/form/lettings/questions/referral_justice.rb
create mode 100644 app/models/form/lettings/questions/referral_la.rb
create mode 100644 app/models/form/lettings/questions/referral_type.rb
create mode 100644 db/migrate/20250225180643_add_referral_type_to_lettings_logs.rb
rename spec/models/form/lettings/questions/{referral_prp_spec.rb => referral_general_needs_prp_spec.rb} (97%)
rename spec/models/form/lettings/questions/{referral_spec.rb => referral_general_needs_spec.rb} (97%)
diff --git a/app/models/derived_variables/lettings_log_variables.rb b/app/models/derived_variables/lettings_log_variables.rb
index 1e2aab790..4eaa5dbff 100644
--- a/app/models/derived_variables/lettings_log_variables.rb
+++ b/app/models/derived_variables/lettings_log_variables.rb
@@ -142,6 +142,9 @@ module DerivedVariables::LettingsLogVariables
self.is_la_inferred = false
end
+ self.referral = 7 if referral_type == 6
+ self.referral = 16 if referral_type == 7
+
reset_address_fields! if is_supported_housing?
set_checkbox_values!
diff --git a/app/models/form/lettings/pages/referral_direct.rb b/app/models/form/lettings/pages/referral_direct.rb
new file mode 100644
index 000000000..df05aa997
--- /dev/null
+++ b/app/models/form/lettings/pages/referral_direct.rb
@@ -0,0 +1,11 @@
+class Form::Lettings::Pages::ReferralDirect < ::Form::Page
+ def initialize(id, hsh, subsection)
+ super
+ @id = "referral_direct"
+ @depends_on = [{ "referral_type" => 1 }]
+ end
+
+ def questions
+ @questions ||= [Form::Lettings::Questions::ReferralDirect.new(nil, nil, self)]
+ end
+end
diff --git a/app/models/form/lettings/pages/referral.rb b/app/models/form/lettings/pages/referral_general_needs.rb
similarity index 64%
rename from app/models/form/lettings/pages/referral.rb
rename to app/models/form/lettings/pages/referral_general_needs.rb
index 8b6fcadbb..5522d1f23 100644
--- a/app/models/form/lettings/pages/referral.rb
+++ b/app/models/form/lettings/pages/referral_general_needs.rb
@@ -1,4 +1,4 @@
-class Form::Lettings::Pages::Referral < ::Form::Page
+class Form::Lettings::Pages::ReferralGeneralNeeds < ::Form::Page
def initialize(id, hsh, subsection)
super
@id = "referral"
@@ -7,6 +7,6 @@ class Form::Lettings::Pages::Referral < ::Form::Page
end
def questions
- @questions ||= [Form::Lettings::Questions::Referral.new(nil, nil, self)]
+ @questions ||= [Form::Lettings::Questions::ReferralGeneralNeeds.new(nil, nil, self)]
end
end
diff --git a/app/models/form/lettings/pages/referral_general_needs_prp.rb b/app/models/form/lettings/pages/referral_general_needs_prp.rb
new file mode 100644
index 000000000..e3206ebdb
--- /dev/null
+++ b/app/models/form/lettings/pages/referral_general_needs_prp.rb
@@ -0,0 +1,12 @@
+class Form::Lettings::Pages::ReferralGeneralNeedsPrp < ::Form::Page
+ def initialize(id, hsh, subsection)
+ super
+ @id = "referral_prp"
+ @copy_key = "lettings.household_situation.referral.general_needs.prp"
+ @depends_on = [{ "owning_organisation_provider_type" => "PRP", "needstype" => 1, "renewal" => 0 }]
+ end
+
+ def questions
+ @questions ||= [Form::Lettings::Questions::ReferralGeneralNeedsPrp.new(nil, nil, self)]
+ end
+end
diff --git a/app/models/form/lettings/pages/referral_hsc.rb b/app/models/form/lettings/pages/referral_hsc.rb
new file mode 100644
index 000000000..596852947
--- /dev/null
+++ b/app/models/form/lettings/pages/referral_hsc.rb
@@ -0,0 +1,11 @@
+class Form::Lettings::Pages::ReferralHsc < ::Form::Page
+ def initialize(id, hsh, subsection)
+ super
+ @id = "referral_hsc"
+ @depends_on = [{ "referral_type" => 4 }]
+ end
+
+ def questions
+ @questions ||= [Form::Lettings::Questions::ReferralHsc.new(nil, nil, self)]
+ end
+end
diff --git a/app/models/form/lettings/pages/referral_justice.rb b/app/models/form/lettings/pages/referral_justice.rb
new file mode 100644
index 000000000..fa10bb727
--- /dev/null
+++ b/app/models/form/lettings/pages/referral_justice.rb
@@ -0,0 +1,11 @@
+class Form::Lettings::Pages::ReferralJustice < ::Form::Page
+ def initialize(id, hsh, subsection)
+ super
+ @id = "referral_justice"
+ @depends_on = [{ "referral_type" => 5 }]
+ end
+
+ def questions
+ @questions ||= [Form::Lettings::Questions::ReferralJustice.new(nil, nil, self)]
+ end
+end
diff --git a/app/models/form/lettings/pages/referral_la.rb b/app/models/form/lettings/pages/referral_la.rb
new file mode 100644
index 000000000..3f04f3aaf
--- /dev/null
+++ b/app/models/form/lettings/pages/referral_la.rb
@@ -0,0 +1,11 @@
+class Form::Lettings::Pages::ReferralLa < ::Form::Page
+ def initialize(id, hsh, subsection)
+ super
+ @id = "referral_la"
+ @depends_on = [{ "referral_type" => 2 }]
+ end
+
+ def questions
+ @questions ||= [Form::Lettings::Questions::ReferralLa.new(nil, nil, self)]
+ end
+end
diff --git a/app/models/form/lettings/pages/referral_prp.rb b/app/models/form/lettings/pages/referral_prp.rb
index baeb01784..8d25edc44 100644
--- a/app/models/form/lettings/pages/referral_prp.rb
+++ b/app/models/form/lettings/pages/referral_prp.rb
@@ -2,8 +2,7 @@ class Form::Lettings::Pages::ReferralPrp < ::Form::Page
def initialize(id, hsh, subsection)
super
@id = "referral_prp"
- @copy_key = "lettings.household_situation.referral.general_needs.prp"
- @depends_on = [{ "owning_organisation_provider_type" => "PRP", "needstype" => 1, "renewal" => 0 }]
+ @depends_on = [{ "referral_type" => 3 }]
end
def questions
diff --git a/app/models/form/lettings/pages/referral_type.rb b/app/models/form/lettings/pages/referral_type.rb
new file mode 100644
index 000000000..3cca2ca2b
--- /dev/null
+++ b/app/models/form/lettings/pages/referral_type.rb
@@ -0,0 +1,10 @@
+class Form::Lettings::Pages::ReferralType < ::Form::Page
+ def initialize(id, hsh, subsection)
+ super
+ @id = "referral_type"
+ end
+
+ def questions
+ @questions ||= [Form::Lettings::Questions::ReferralType.new(nil, nil, self)]
+ end
+end
diff --git a/app/models/form/lettings/questions/referral_direct.rb b/app/models/form/lettings/questions/referral_direct.rb
new file mode 100644
index 000000000..ddadcc8b7
--- /dev/null
+++ b/app/models/form/lettings/questions/referral_direct.rb
@@ -0,0 +1,26 @@
+class Form::Lettings::Questions::ReferralDirect < ::Form::Question
+ def initialize(id, hsh, page)
+ super
+ @id = "referral"
+ @copy_key = "lettings.household_situation.referral.direct"
+ @type = "radio"
+ @check_answers_card_number = 0
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ end
+
+ def answer_options
+ {
+ "20" => {
+ "value" => "Homeless households owed a duty and not on a housing register or waiting list",
+ },
+ "2" => {
+ "value" => "Tenant applied directly for an available property",
+ },
+ "8" => {
+ "value" => "Relocated through official housing mobility scheme",
+ },
+ }.freeze
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2025 => 84 }.freeze
+end
diff --git a/app/models/form/lettings/questions/referral.rb b/app/models/form/lettings/questions/referral_general_needs.rb
similarity index 97%
rename from app/models/form/lettings/questions/referral.rb
rename to app/models/form/lettings/questions/referral_general_needs.rb
index 98e5a9186..6efdfc1f0 100644
--- a/app/models/form/lettings/questions/referral.rb
+++ b/app/models/form/lettings/questions/referral_general_needs.rb
@@ -1,4 +1,4 @@
-class Form::Lettings::Questions::Referral < ::Form::Question
+class Form::Lettings::Questions::ReferralGeneralNeeds < ::Form::Question
def initialize(id, hsh, page)
super
@id = "referral"
diff --git a/app/models/form/lettings/questions/referral_general_needs_prp.rb b/app/models/form/lettings/questions/referral_general_needs_prp.rb
new file mode 100644
index 000000000..afd26117b
--- /dev/null
+++ b/app/models/form/lettings/questions/referral_general_needs_prp.rb
@@ -0,0 +1,105 @@
+class Form::Lettings::Questions::ReferralGeneralNeedsPrp < ::Form::Question
+ def initialize(id, hsh, page)
+ super
+ @id = "referral"
+ @copy_key = "lettings.household_situation.referral.general_needs.prp"
+ @type = "radio"
+ @check_answers_card_number = 0
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ end
+
+ def answer_options
+ if form.start_year_2024_or_later?
+ {
+ "1" => {
+ "value" => "Internal transfer",
+ "hint" => "Where the tenant has moved to another social property owned by the same landlord.",
+ },
+ "2" => {
+ "value" => "Tenant applied directly (no referral or nomination)",
+ },
+ "3" => {
+ "value" => "Nominated by a local housing authority",
+ },
+ "8" => {
+ "value" => "Re-located through official housing mobility scheme",
+ },
+ "10" => {
+ "value" => "Other social landlord",
+ },
+ "9" => {
+ "value" => "Community learning disability team",
+ },
+ "14" => {
+ "value" => "Community mental health team",
+ },
+ "15" => {
+ "value" => "Health service",
+ },
+ "18" => {
+ "value" => "Police, probation, prison or youth offending team – tenant had custodial sentence",
+ },
+ "19" => {
+ "value" => "Police, probation, prison or youth offending team – no custodial sentence",
+ },
+ "7" => {
+ "value" => "Voluntary agency",
+ },
+ "17" => {
+ "value" => "Children’s Social Care",
+ },
+ "16" => {
+ "value" => "Other",
+ },
+ }.freeze
+ else
+ {
+ "1" => {
+ "value" => "Internal transfer",
+ "hint" => "Where the tenant has moved to another social property owned by the same landlord.",
+ },
+ "2" => {
+ "value" => "Tenant applied directly (no referral or nomination)",
+ },
+ "3" => {
+ "value" => "Nominated by a local housing authority",
+ },
+ "4" => {
+ "value" => "Referred by local authority housing department",
+ },
+ "8" => {
+ "value" => "Re-located through official housing mobility scheme",
+ },
+ "10" => {
+ "value" => "Other social landlord",
+ },
+ "9" => {
+ "value" => "Community learning disability team",
+ },
+ "14" => {
+ "value" => "Community mental health team",
+ },
+ "15" => {
+ "value" => "Health service",
+ },
+ "12" => {
+ "value" => "Police, probation or prison",
+ },
+ "7" => {
+ "value" => "Voluntary agency",
+ },
+ "13" => {
+ "value" => "Youth offending team",
+ },
+ "17" => {
+ "value" => "Children’s Social Care",
+ },
+ "16" => {
+ "value" => "Other",
+ },
+ }.freeze
+ end
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2023 => 85, 2024 => 84 }.freeze
+end
diff --git a/app/models/form/lettings/questions/referral_hsc.rb b/app/models/form/lettings/questions/referral_hsc.rb
new file mode 100644
index 000000000..a5b9c32f0
--- /dev/null
+++ b/app/models/form/lettings/questions/referral_hsc.rb
@@ -0,0 +1,32 @@
+class Form::Lettings::Questions::ReferralHsc < ::Form::Question
+ def initialize(id, hsh, page)
+ super
+ @id = "referral"
+ @copy_key = "lettings.household_situation.referral.hsc"
+ @type = "radio"
+ @check_answers_card_number = 0
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ end
+
+ def answer_options
+ {
+ "15" => {
+ "value" => "Health service",
+ },
+ "9" => {
+ "value" => "Community learning disability team",
+ },
+ "14" => {
+ "value" => "Community mental health team",
+ },
+ "24" => {
+ "value" => "Adult social services",
+ },
+ "17" => {
+ "value" => "Children's social care",
+ },
+ }.freeze
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2025 => 84 }.freeze
+end
diff --git a/app/models/form/lettings/questions/referral_justice.rb b/app/models/form/lettings/questions/referral_justice.rb
new file mode 100644
index 000000000..0e02e0c42
--- /dev/null
+++ b/app/models/form/lettings/questions/referral_justice.rb
@@ -0,0 +1,23 @@
+class Form::Lettings::Questions::ReferralJustice < ::Form::Question
+ def initialize(id, hsh, page)
+ super
+ @id = "referral"
+ @copy_key = "lettings.household_situation.referral.justice"
+ @type = "radio"
+ @check_answers_card_number = 0
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ end
+
+ def answer_options
+ {
+ "18" => {
+ "value" => "With a custodial sentence",
+ },
+ "19" => {
+ "value" => "No custodial sentence",
+ },
+ }.freeze
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2025 => 84 }.freeze
+end
diff --git a/app/models/form/lettings/questions/referral_la.rb b/app/models/form/lettings/questions/referral_la.rb
new file mode 100644
index 000000000..7a654df88
--- /dev/null
+++ b/app/models/form/lettings/questions/referral_la.rb
@@ -0,0 +1,29 @@
+class Form::Lettings::Questions::ReferralLa < ::Form::Question
+ def initialize(id, hsh, page)
+ super
+ @id = "referral"
+ @copy_key = "lettings.household_situation.referral.la"
+ @type = "radio"
+ @check_answers_card_number = 0
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ end
+
+ def answer_options
+ {
+ "21" => {
+ "value" => "Local authority lettings",
+ },
+ "3" => {
+ "value" => "PRP lettings nominated by a local authority",
+ },
+ "4" => {
+ "value" => "PRP support lettings referred by a local authority",
+ },
+ "22" => {
+ "value" => "Other",
+ },
+ }.freeze
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2025 => 84 }.freeze
+end
diff --git a/app/models/form/lettings/questions/referral_prp.rb b/app/models/form/lettings/questions/referral_prp.rb
index 96da2cba3..44799bb8c 100644
--- a/app/models/form/lettings/questions/referral_prp.rb
+++ b/app/models/form/lettings/questions/referral_prp.rb
@@ -2,104 +2,25 @@ class Form::Lettings::Questions::ReferralPrp < ::Form::Question
def initialize(id, hsh, page)
super
@id = "referral"
- @copy_key = "lettings.household_situation.referral.general_needs.prp"
+ @copy_key = "lettings.household_situation.referral.prp"
@type = "radio"
@check_answers_card_number = 0
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
def answer_options
- if form.start_year_2024_or_later?
- {
- "1" => {
- "value" => "Internal transfer",
- "hint" => "Where the tenant has moved to another social property owned by the same landlord.",
- },
- "2" => {
- "value" => "Tenant applied directly (no referral or nomination)",
- },
- "3" => {
- "value" => "Nominated by a local housing authority",
- },
- "8" => {
- "value" => "Re-located through official housing mobility scheme",
- },
- "10" => {
- "value" => "Other social landlord",
- },
- "9" => {
- "value" => "Community learning disability team",
- },
- "14" => {
- "value" => "Community mental health team",
- },
- "15" => {
- "value" => "Health service",
- },
- "18" => {
- "value" => "Police, probation, prison or youth offending team – tenant had custodial sentence",
- },
- "19" => {
- "value" => "Police, probation, prison or youth offending team – no custodial sentence",
- },
- "7" => {
- "value" => "Voluntary agency",
- },
- "17" => {
- "value" => "Children’s Social Care",
- },
- "16" => {
- "value" => "Other",
- },
- }.freeze
- else
- {
- "1" => {
- "value" => "Internal transfer",
- "hint" => "Where the tenant has moved to another social property owned by the same landlord.",
- },
- "2" => {
- "value" => "Tenant applied directly (no referral or nomination)",
- },
- "3" => {
- "value" => "Nominated by a local housing authority",
- },
- "4" => {
- "value" => "Referred by local authority housing department",
- },
- "8" => {
- "value" => "Re-located through official housing mobility scheme",
- },
- "10" => {
- "value" => "Other social landlord",
- },
- "9" => {
- "value" => "Community learning disability team",
- },
- "14" => {
- "value" => "Community mental health team",
- },
- "15" => {
- "value" => "Health service",
- },
- "12" => {
- "value" => "Police, probation or prison",
- },
- "7" => {
- "value" => "Voluntary agency",
- },
- "13" => {
- "value" => "Youth offending team",
- },
- "17" => {
- "value" => "Children’s Social Care",
- },
- "16" => {
- "value" => "Other",
- },
- }.freeze
- end
+ {
+ "1" => {
+ "value" => "Internal transfer from another property with the same landlord",
+ },
+ "10" => {
+ "value" => "A different PRP landlord",
+ },
+ "23" => {
+ "value" => "Other",
+ },
+ }.freeze
end
- QUESTION_NUMBER_FROM_YEAR = { 2023 => 85, 2024 => 84 }.freeze
+ QUESTION_NUMBER_FROM_YEAR = { 2025 => 84 }.freeze
end
diff --git a/app/models/form/lettings/questions/referral_type.rb b/app/models/form/lettings/questions/referral_type.rb
new file mode 100644
index 000000000..5ff0f411e
--- /dev/null
+++ b/app/models/form/lettings/questions/referral_type.rb
@@ -0,0 +1,38 @@
+class Form::Lettings::Questions::ReferralType < ::Form::Question
+ def initialize(id, hsh, page)
+ super
+ @id = "referral_type"
+ @copy_key = "lettings.household_situation.referral.type"
+ @type = "radio"
+ @check_answers_card_number = 0
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ end
+
+ def answer_options
+ {
+ "1" => {
+ "value" => "Direct",
+ },
+ "2" => {
+ "value" => "From a local authority housing register or waiting list",
+ },
+ "3" => {
+ "value" => "From a PRP-only housing register or waiting list (no local authority involvement)",
+ },
+ "4" => {
+ "value" => "Health and social care services",
+ },
+ "5" => {
+ "value" => "Police, probation, prison or youth offending team",
+ },
+ "6" => {
+ "value" => "Voluntary agency",
+ },
+ "7" => {
+ "value" => "Other",
+ },
+ }.freeze
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2025 => 84 }.freeze
+end
diff --git a/app/models/form/lettings/subsections/household_situation.rb b/app/models/form/lettings/subsections/household_situation.rb
index dc3fd608b..8bf747f01 100644
--- a/app/models/form/lettings/subsections/household_situation.rb
+++ b/app/models/form/lettings/subsections/household_situation.rb
@@ -21,11 +21,28 @@ class Form::Lettings::Subsections::HouseholdSituation < ::Form::Subsection
Form::Lettings::Pages::ReasonablePreference.new("reasonable_preference", nil, self),
Form::Lettings::Pages::ReasonablePreferenceReason.new(nil, nil, self),
Form::Lettings::Pages::AllocationSystem.new("allocation_system", nil, self),
- Form::Lettings::Pages::Referral.new(nil, nil, self),
- Form::Lettings::Pages::ReferralPrp.new(nil, nil, self),
- Form::Lettings::Pages::ReferralSupportedHousing.new(nil, nil, self),
- Form::Lettings::Pages::ReferralSupportedHousingPrp.new(nil, nil, self),
+ referral_questions,
Form::Lettings::Pages::ReferralValueCheck.new(nil, nil, self),
- ].compact
+ ].flatten.compact
+ end
+
+ def referral_questions
+ if form.start_year_2025_or_later?
+ [
+ Form::Lettings::Pages::ReferralType.new(nil, nil, self),
+ Form::Lettings::Pages::ReferralDirect.new(nil, nil, self),
+ Form::Lettings::Pages::ReferralLa.new(nil, nil, self),
+ Form::Lettings::Pages::ReferralPrp.new(nil, nil, self),
+ Form::Lettings::Pages::ReferralHsc.new(nil, nil, self),
+ Form::Lettings::Pages::ReferralJustice.new(nil, nil, self),
+ ]
+ else
+ [
+ Form::Lettings::Pages::ReferralGeneralNeeds.new(nil, nil, self),
+ Form::Lettings::Pages::ReferralGeneralNeedsPrp.new(nil, nil, self),
+ Form::Lettings::Pages::ReferralSupportedHousing.new(nil, nil, self),
+ Form::Lettings::Pages::ReferralSupportedHousingPrp.new(nil, nil, self),
+ ]
+ end
end
end
diff --git a/app/models/validations/household_validations.rb b/app/models/validations/household_validations.rb
index 63da6d628..723ab30b6 100644
--- a/app/models/validations/household_validations.rb
+++ b/app/models/validations/household_validations.rb
@@ -32,6 +32,7 @@ module Validations::HouseholdValidations
if record.is_reason_permanently_decanted? && record.referral.present? && !record.is_internal_transfer?
record.errors.add :referral, I18n.t("validations.lettings.household.referral.leaving_last_settled_home.reason_permanently_decanted")
+ record.errors.add :referral_type, I18n.t("validations.lettings.household.referral.leaving_last_settled_home.reason_permanently_decanted")
record.errors.add :reason, I18n.t("validations.lettings.household.reason.leaving_last_settled_home.not_internal_transfer")
end
@@ -171,6 +172,7 @@ module Validations::HouseholdValidations
label = record.form.get_question("prevten", record).present? ? record.form.get_question("prevten", record).label_from_value(record.prevten) : ""
record.errors.add :prevten, :internal_transfer_non_social_housing, message: I18n.t("validations.lettings.household.prevten.internal_transfer", prevten: label)
record.errors.add :referral, :internal_transfer_non_social_housing, message: I18n.t("validations.lettings.household.referral.prevten_invalid", prevten: label)
+ record.errors.add :referral_type, :internal_transfer_non_social_housing, message: I18n.t("validations.lettings.household.referral.prevten_invalid", prevten: label)
end
end
@@ -180,6 +182,7 @@ module Validations::HouseholdValidations
if record.is_internal_transfer? && record.owning_organisation.provider_type == "PRP" && record.is_prevten_la_general_needs?
record.errors.add :prevten, :internal_transfer_fixed_or_lifetime, message: I18n.t("validations.lettings.household.prevten.la_general_needs.internal_transfer")
record.errors.add :referral, :internal_transfer_fixed_or_lifetime, message: I18n.t("validations.lettings.household.referral.la_general_needs.internal_transfer")
+ record.errors.add :referral_type, :internal_transfer_fixed_or_lifetime, message: I18n.t("validations.lettings.household.referral.la_general_needs.internal_transfer")
end
end
diff --git a/app/models/validations/property_validations.rb b/app/models/validations/property_validations.rb
index 1cf710857..364cfe732 100644
--- a/app/models/validations/property_validations.rb
+++ b/app/models/validations/property_validations.rb
@@ -11,6 +11,7 @@ module Validations::PropertyValidations
if record.is_relet_to_temp_tenant? && REFERRAL_INVALID_TMP.include?(record.referral)
record.errors.add :rsnvac, I18n.t("validations.lettings.property.rsnvac.referral_invalid")
record.errors.add :referral, :referral_invalid, message: I18n.t("validations.lettings.property.referral.rsnvac_non_temp")
+ record.errors.add :referral_type, :referral_invalid, message: I18n.t("validations.lettings.property.referral.rsnvac_non_temp")
end
if record.renewal.present? && record.renewal.zero? && record.rsnvac == 14
diff --git a/app/services/bulk_upload/lettings/year2025/row_parser.rb b/app/services/bulk_upload/lettings/year2025/row_parser.rb
index 3953d7afb..26b2e39f9 100644
--- a/app/services/bulk_upload/lettings/year2025/row_parser.rb
+++ b/app/services/bulk_upload/lettings/year2025/row_parser.rb
@@ -1094,6 +1094,7 @@ private
accessible_register: %i[field_115],
letting_allocation: %i[field_112 field_113 field_114 field_115],
+ referral_type: %i[field_116],
referral: %i[field_116],
net_income_known: %i[field_117],
@@ -1279,6 +1280,7 @@ private
attributes["accessible_register"] = accessible_register
attributes["letting_allocation_unknown"] = letting_allocation_unknown
+ attributes["referral_type"] = referral_type
attributes["referral"] = field_116
attributes["net_income_known"] = net_income_known
@@ -1663,4 +1665,22 @@ private
"R" # refused
end
end
+
+ def referral_type
+ mapping = {
+ 1 => [20, 2, 8],
+ 2 => [21, 3, 4, 22],
+ 3 => [1, 10, 23],
+ 4 => [15, 9, 14, 24, 17],
+ 5 => [18, 19],
+ 6 => [7],
+ 7 => [16],
+ }
+
+ mapping.each do |key, values|
+ return key if values.include?(field_116)
+ end
+
+ 0
+ end
end
diff --git a/config/locales/forms/2025/lettings/household_situation.en.yml b/config/locales/forms/2025/lettings/household_situation.en.yml
index fbbdcf657..22c7052eb 100644
--- a/config/locales/forms/2025/lettings/household_situation.en.yml
+++ b/config/locales/forms/2025/lettings/household_situation.en.yml
@@ -112,29 +112,39 @@ en:
question_text: "How was this letting allocated?"
referral:
- supported_housing:
- prp:
- page_header: ""
- check_answer_label: "Source of referral for letting"
- check_answer_prompt: ""
- hint_text: ""
- question_text: "What was the source of referral for this letting?"
- la:
- page_header: ""
- check_answer_label: "Source of referral for letting"
- check_answer_prompt: ""
- hint_text: "You told us that you are a local authority. We have removed some options because of this."
- question_text: "What was the source of referral for this letting?"
- general_needs:
- prp:
- page_header: ""
- check_answer_label: "Source of referral for letting"
- check_answer_prompt: ""
- hint_text: "You told us that the needs type is general needs. We have removed some options because of this."
- question_text: "What was the source of referral for this letting?"
- la:
- page_header: ""
- check_answer_label: "Source of referral for letting"
- check_answer_prompt: ""
- hint_text: "You told us that you are a local authority and that the needs type is general needs. We have removed some options because of this."
- question_text: "What was the source of referral for this letting?"
+ type:
+ page_header: ""
+ check_answer_label: "Source of referral for letting"
+ check_answer_prompt: "Select source of referral"
+ hint_text: ""
+ question_text: "What was the source of referral for this letting?"
+ direct:
+ page_header: ""
+ check_answer_label: "Source of referral for letting"
+ check_answer_prompt: "Select source of referral"
+ hint_text: ""
+ question_text: "What was the source of referral for this letting?"
+ la:
+ page_header: ""
+ check_answer_label: "Source of referral for letting"
+ check_answer_prompt: "Select source of referral"
+ hint_text: ""
+ question_text: "What was the source of referral for this letting?"
+ prp:
+ page_header: ""
+ check_answer_label: "Source of referral for letting"
+ check_answer_prompt: "Select source of referral"
+ hint_text: ""
+ question_text: "What was the source of referral for this letting?"
+ hsc:
+ page_header: ""
+ check_answer_label: "Source of referral for letting"
+ check_answer_prompt: "Select source of referral"
+ hint_text: ""
+ question_text: "What was the source of referral for this letting?"
+ justice:
+ page_header: ""
+ check_answer_label: "Source of referral for letting"
+ check_answer_prompt: "Select source of referral"
+ hint_text: ""
+ question_text: "What was the source of referral for this letting?"
diff --git a/db/migrate/20250225180643_add_referral_type_to_lettings_logs.rb b/db/migrate/20250225180643_add_referral_type_to_lettings_logs.rb
new file mode 100644
index 000000000..4df8fe9dc
--- /dev/null
+++ b/db/migrate/20250225180643_add_referral_type_to_lettings_logs.rb
@@ -0,0 +1,5 @@
+class AddReferralTypeToLettingsLogs < ActiveRecord::Migration[7.2]
+ def change
+ add_column :lettings_logs, :referral_type, :integer
+ end
+end
diff --git a/db/schema.rb b/db/schema.rb
index 894bb1638..20a836eed 100644
--- a/db/schema.rb
+++ b/db/schema.rb
@@ -10,7 +10,7 @@
#
# It's strongly recommended that you check this file into your version control system.
-ActiveRecord::Schema[7.2].define(version: 2025_01_10_150609) do
+ActiveRecord::Schema[7.2].define(version: 2025_02_25_180643) do
# These are extensions that must be enabled in order to support this database
enable_extension "plpgsql"
@@ -373,6 +373,8 @@ ActiveRecord::Schema[7.2].define(version: 2025_01_10_150609) do
t.integer "partner_under_16_value_check"
t.integer "multiple_partners_value_check"
t.bigint "created_by_id"
+ t.integer "referral_type"
+ t.boolean "manual_address_entry_selected", default: false
t.index ["assigned_to_id"], name: "index_lettings_logs_on_assigned_to_id"
t.index ["bulk_upload_id"], name: "index_lettings_logs_on_bulk_upload_id"
t.index ["created_by_id"], name: "index_lettings_logs_on_created_by_id"
diff --git a/spec/factories/lettings_log.rb b/spec/factories/lettings_log.rb
index c8c51ecf3..5d13cacfa 100644
--- a/spec/factories/lettings_log.rb
+++ b/spec/factories/lettings_log.rb
@@ -159,6 +159,7 @@ FactoryBot.define do
is_carehome { 0 }
declaration { 1 }
first_time_property_let_as_social_housing { 0 }
+ referral_type { 1 }
referral { 2 }
uprn_known { 0 }
joint { 3 }
diff --git a/spec/models/form/lettings/questions/referral_prp_spec.rb b/spec/models/form/lettings/questions/referral_general_needs_prp_spec.rb
similarity index 97%
rename from spec/models/form/lettings/questions/referral_prp_spec.rb
rename to spec/models/form/lettings/questions/referral_general_needs_prp_spec.rb
index a10b6d383..832394bcc 100644
--- a/spec/models/form/lettings/questions/referral_prp_spec.rb
+++ b/spec/models/form/lettings/questions/referral_general_needs_prp_spec.rb
@@ -1,6 +1,6 @@
require "rails_helper"
-RSpec.describe Form::Lettings::Questions::ReferralPrp, type: :model do
+RSpec.describe Form::Lettings::Questions::ReferralGeneralNeedsPrp, type: :model do
subject(:question) { described_class.new(question_id, question_definition, page) }
let(:question_id) { nil }
diff --git a/spec/models/form/lettings/questions/referral_spec.rb b/spec/models/form/lettings/questions/referral_general_needs_spec.rb
similarity index 97%
rename from spec/models/form/lettings/questions/referral_spec.rb
rename to spec/models/form/lettings/questions/referral_general_needs_spec.rb
index 75e6c2f42..2f7c7a864 100644
--- a/spec/models/form/lettings/questions/referral_spec.rb
+++ b/spec/models/form/lettings/questions/referral_general_needs_spec.rb
@@ -1,6 +1,6 @@
require "rails_helper"
-RSpec.describe Form::Lettings::Questions::Referral, type: :model do
+RSpec.describe Form::Lettings::Questions::ReferralGeneralNeeds, type: :model do
subject(:question) { described_class.new(question_id, question_definition, page) }
let(:question_id) { nil }
diff --git a/spec/models/form/lettings/subsections/household_situation_spec.rb b/spec/models/form/lettings/subsections/household_situation_spec.rb
index d672b3ccc..eb056ca7a 100644
--- a/spec/models/form/lettings/subsections/household_situation_spec.rb
+++ b/spec/models/form/lettings/subsections/household_situation_spec.rb
@@ -19,6 +19,7 @@ RSpec.describe Form::Lettings::Subsections::HouseholdSituation, type: :model do
context "with form year before 2024" do
before do
allow(form).to receive(:start_year_2024_or_later?).and_return(false)
+ allow(form).to receive(:start_year_2025_or_later?).and_return(false)
end
it "has correct pages" do
@@ -46,9 +47,10 @@ RSpec.describe Form::Lettings::Subsections::HouseholdSituation, type: :model do
end
end
- context "with form year >= 2024" do
+ context "with form year is 2024" do
before do
allow(form).to receive(:start_year_2024_or_later?).and_return(true)
+ allow(form).to receive(:start_year_2025_or_later?).and_return(false)
end
it "has correct pages" do
@@ -77,6 +79,40 @@ RSpec.describe Form::Lettings::Subsections::HouseholdSituation, type: :model do
end
end
+ context "with form year is 2025" do
+ before do
+ allow(form).to receive(:start_year_2024_or_later?).and_return(true)
+ allow(form).to receive(:start_year_2025_or_later?).and_return(true)
+ end
+
+ it "has correct pages" do
+ expect(household_situation.pages.map(&:id)).to eq(
+ %w[
+ time_lived_in_local_authority
+ time_on_waiting_list
+ reason_for_leaving_last_settled_home
+ reason_for_leaving_last_settled_home_renewal
+ reasonother_value_check
+ previous_housing_situation
+ previous_housing_situation_renewal
+ homelessness
+ previous_postcode
+ previous_local_authority
+ reasonable_preference
+ reasonable_preference_reason
+ allocation_system
+ referral_type
+ referral_direct
+ referral_la
+ referral_prp
+ referral_hsc
+ referral_justice
+ referral_value_check
+ ],
+ )
+ end
+ end
+
it "has the correct id" do
expect(household_situation.id).to eq("household_situation")
end
diff --git a/spec/models/validations/household_validations_spec.rb b/spec/models/validations/household_validations_spec.rb
index b6af03736..2086e55f1 100644
--- a/spec/models/validations/household_validations_spec.rb
+++ b/spec/models/validations/household_validations_spec.rb
@@ -129,33 +129,42 @@ RSpec.describe Validations::HouseholdValidations do
context "when referral is not internal transfer" do
it "cannot be permanently decanted from another property owned by this landlord" do
record.reason = 1
+ record.referral_type = 1
record.referral = 2
household_validator.validate_reason_for_leaving_last_settled_home(record)
expect(record.errors["reason"])
.to include(match(I18n.t("validations.lettings.household.reason.leaving_last_settled_home.not_internal_transfer")))
expect(record.errors["referral"])
.to include(match(I18n.t("validations.lettings.household.referral.leaving_last_settled_home.reason_permanently_decanted")))
+ expect(record.errors["referral_type"])
+ .to include(match(I18n.t("validations.lettings.household.referral.leaving_last_settled_home.reason_permanently_decanted")))
end
end
context "when referral is internal transfer" do
it "can be permanently decanted from another property owned by this landlord" do
record.reason = 1
+ record.referral_type = 3
record.referral = 1
household_validator.validate_reason_for_leaving_last_settled_home(record)
expect(record.errors["reason"])
.to be_empty
expect(record.errors["referral"])
.to be_empty
+ expect(record.errors["referral_type"])
+ .to be_empty
end
it "cannot have a PRP as landlord and Housing situation before this letting cannot be LA general needs" do
record.owning_organisation.provider_type = "PRP"
record.prevten = 30
+ record.referral_type = 3
record.referral = 1
household_validator.validate_referral(record)
expect(record.errors["referral"])
.to include(match(I18n.t("validations.lettings.household.referral.la_general_needs.internal_transfer")))
+ expect(record.errors["referral_type"])
+ .to include(match(I18n.t("validations.lettings.household.referral.la_general_needs.internal_transfer")))
expect(record.errors["prevten"])
.to include(match(I18n.t("validations.lettings.household.prevten.la_general_needs.internal_transfer")))
@@ -163,6 +172,8 @@ RSpec.describe Validations::HouseholdValidations do
household_validator.validate_referral(record)
expect(record.errors["referral"])
.to include(match(I18n.t("validations.lettings.household.referral.la_general_needs.internal_transfer")))
+ expect(record.errors["referral_type"])
+ .to include(match(I18n.t("validations.lettings.household.referral.la_general_needs.internal_transfer")))
expect(record.errors["prevten"])
.to include(match(I18n.t("validations.lettings.household.prevten.la_general_needs.internal_transfer")))
end
@@ -603,37 +614,45 @@ RSpec.describe Validations::HouseholdValidations do
context "when homelessness is assessed" do
it "can be internal transfer" do
record.homeless = 11
+ record.referral_type = 3
record.referral = 1
household_validator.validate_referral(record)
expect(record.errors["referral"]).to be_empty
+ expect(record.errors["referral_type"]).to be_empty
expect(record.errors["homeless"]).to be_empty
end
it "can be non internal transfer" do
record.owning_organisation.provider_type = "PRP"
record.homeless = 0
+ record.referral_type = 2
record.referral = 3
household_validator.validate_referral(record)
expect(record.errors["referral"]).to be_empty
+ expect(record.errors["referral_type"]).to be_empty
expect(record.errors["homeless"]).to be_empty
end
end
context "when homelessness is other" do
it "cannot be internal transfer" do
+ record.referral_type = 3
record.referral = 1
record.homeless = 7
household_validator.validate_referral(record)
expect(record.errors["referral"]).to be_empty
+ expect(record.errors["referral_type"]).to be_empty
expect(record.errors["homeless"]).to be_empty
end
it "can be non internal transfer" do
record.owning_organisation.provider_type = "PRP"
+ record.referral_type = 2
record.referral = 3
record.homeless = 1
household_validator.validate_referral(record)
expect(record.errors["referral"]).to be_empty
+ expect(record.errors["referral_type"]).to be_empty
expect(record.errors["homeless"]).to be_empty
end
end
@@ -715,6 +734,7 @@ RSpec.describe Validations::HouseholdValidations do
context "when the referral is internal transfer" do
it "prevten can be 9" do
+ record.referral_type = 3
record.referral = 1
record.prevten = 9
household_validator.validate_previous_housing_situation(record)
@@ -722,6 +742,8 @@ RSpec.describe Validations::HouseholdValidations do
.to be_empty
expect(record.errors["referral"])
.to be_empty
+ expect(record.errors["referral_type"])
+ .to be_empty
end
[
@@ -740,6 +762,7 @@ RSpec.describe Validations::HouseholdValidations do
{ code: 29, label: "Prison or approved probation hostel" },
].each do |prevten|
it "prevten cannot be #{prevten[:code]}" do
+ record.referral_type = 3
record.referral = 1
record.prevten = prevten[:code]
household_validator.validate_previous_housing_situation(record)
@@ -748,6 +771,8 @@ RSpec.describe Validations::HouseholdValidations do
.to include(match I18n.t("validations.lettings.household.prevten.internal_transfer", prevten: label))
expect(record.errors["referral"])
.to include(match I18n.t("validations.lettings.household.referral.prevten_invalid", prevten: ""))
+ expect(record.errors["referral_type"])
+ .to include(match I18n.t("validations.lettings.household.referral.prevten_invalid", prevten: ""))
end
end
end
diff --git a/spec/models/validations/property_validations_spec.rb b/spec/models/validations/property_validations_spec.rb
index 142cb2491..88939959b 100644
--- a/spec/models/validations/property_validations_spec.rb
+++ b/spec/models/validations/property_validations_spec.rb
@@ -168,6 +168,7 @@ RSpec.describe Validations::PropertyValidations do
it "expects that the letting source can be a referral" do
log.prevten = 0
+ log.referral_type = 1
log.referral = 2
property_validator.validate_rsnvac(log)
expect(log.errors["rsnvac"]).to be_empty
From c54cf1134832a81f41e65063e0559e806cf52e7e Mon Sep 17 00:00:00 2001
From: Manny Dinssa <44172848+Dinssa@users.noreply.github.com>
Date: Thu, 6 Mar 2025 08:38:55 +0000
Subject: [PATCH 5/6] CLDC-3860: Bulk upload add validation, prevent reasonpref
dontknow being selected (#2955)
* Add validation on reasonpref dontknow
* Add test
* Update method
* Update setting errors
* Update test
* Add tests for rake task
* separate out tests
* Test updated at, excluding pre 2024
* Update 2025 row parser
* Clear values if rp_dontknow conflict exists
* Reorder, no change just precautionary
* Put back code removed
---
.../lettings/year2024/row_parser.rb | 31 ++++++--
.../lettings/year2025/row_parser.rb | 31 ++++++--
.../lettings/2024/bulk_upload.en.yml | 4 ++
.../lettings/2025/bulk_upload.en.yml | 4 ++
...calculate_invalid_reasonpref_dontknow.rake | 12 ++++
...culate_invalid_reasonpref_dontknow_spec.rb | 70 +++++++++++++++++++
.../lettings/year2024/row_parser_spec.rb | 18 ++++-
.../lettings/year2025/row_parser_spec.rb | 13 ++++
8 files changed, 171 insertions(+), 12 deletions(-)
create mode 100644 lib/tasks/recalculate_invalid_reasonpref_dontknow.rake
create mode 100644 spec/lib/tasks/recalculate_invalid_reasonpref_dontknow_spec.rb
diff --git a/app/services/bulk_upload/lettings/year2024/row_parser.rb b/app/services/bulk_upload/lettings/year2024/row_parser.rb
index acf5d6467..2b3aae5d5 100644
--- a/app/services/bulk_upload/lettings/year2024/row_parser.rb
+++ b/app/services/bulk_upload/lettings/year2024/row_parser.rb
@@ -418,6 +418,7 @@ class BulkUpload::Lettings::Year2024::RowParser
validate :validate_no_and_dont_know_disabled_needs_conjunction, on: :after_log
validate :validate_no_housing_needs_questions_answered, on: :after_log
validate :validate_reasonable_preference_homeless, on: :after_log
+ validate :validate_reasonable_preference_dont_know, on: :after_log
validate :validate_condition_effects, on: :after_log
validate :validate_if_log_already_exists, on: :after_log, if: -> { FeatureToggle.bulk_upload_duplicate_log_check_enabled? }
@@ -751,6 +752,15 @@ private
end
end
+ def validate_reasonable_preference_dont_know
+ if rp_dontknow_conflict?
+ errors.add(:field_111, I18n.t("#{ERROR_BASE_KEY}.reasonpref.conflict.dont_know"))
+ %i[field_107 field_108 field_109 field_110].each do |field|
+ errors.add(field, I18n.t("#{ERROR_BASE_KEY}.reasonpref.conflict.other")) if send(field) == 1
+ end
+ end
+ end
+
def validate_reasonable_preference_homeless
reason_fields = %i[field_107 field_108 field_109 field_110 field_111]
if field_106 == 1 && reason_fields.all? { |field| attributes[field.to_s].blank? }
@@ -1270,11 +1280,11 @@ private
attributes["ppostcode_full"] = ppostcode_full
attributes["reasonpref"] = field_106
- attributes["rp_homeless"] = field_107
- attributes["rp_insan_unsat"] = field_108
- attributes["rp_medwel"] = field_109
- attributes["rp_hardship"] = field_110
- attributes["rp_dontknow"] = field_111
+ attributes["rp_homeless"] = field_107 unless rp_dontknow_conflict?
+ attributes["rp_insan_unsat"] = field_108 unless rp_dontknow_conflict?
+ attributes["rp_medwel"] = field_109 unless rp_dontknow_conflict?
+ attributes["rp_hardship"] = field_110 unless rp_dontknow_conflict?
+ attributes["rp_dontknow"] = field_111 unless rp_dontknow_conflict?
attributes["cbl"] = cbl
attributes["chr"] = chr
@@ -1661,4 +1671,15 @@ private
def bulk_upload_organisation
Organisation.find(bulk_upload.organisation_id)
end
+
+ def rp_dontknow_conflict?
+ other_reason_fields = %i[field_107 field_108 field_109 field_110]
+ if field_106 == 1
+ selected_reasons = other_reason_fields.select { |field| send(field) == 1 }
+ dont_know_selected = field_111 == 1
+
+ return true if selected_reasons.any? && dont_know_selected
+ end
+ false
+ end
end
diff --git a/app/services/bulk_upload/lettings/year2025/row_parser.rb b/app/services/bulk_upload/lettings/year2025/row_parser.rb
index 26b2e39f9..522960aa1 100644
--- a/app/services/bulk_upload/lettings/year2025/row_parser.rb
+++ b/app/services/bulk_upload/lettings/year2025/row_parser.rb
@@ -417,6 +417,7 @@ class BulkUpload::Lettings::Year2025::RowParser
validate :validate_no_and_dont_know_disabled_needs_conjunction, on: :after_log
validate :validate_no_housing_needs_questions_answered, on: :after_log
validate :validate_reasonable_preference_homeless, on: :after_log
+ validate :validate_reasonable_preference_dont_know, on: :after_log
validate :validate_condition_effects, on: :after_log
validate :validate_if_log_already_exists, on: :after_log, if: -> { FeatureToggle.bulk_upload_duplicate_log_check_enabled? }
@@ -750,6 +751,15 @@ private
end
end
+ def validate_reasonable_preference_dont_know
+ if rp_dontknow_conflict?
+ errors.add(:field_111, I18n.t("#{ERROR_BASE_KEY}.reasonpref.conflict.dont_know"))
+ %i[field_107 field_108 field_109 field_110].each do |field|
+ errors.add(field, I18n.t("#{ERROR_BASE_KEY}.reasonpref.conflict.other")) if send(field) == 1
+ end
+ end
+ end
+
def validate_reasonable_preference_homeless
reason_fields = %i[field_107 field_108 field_109 field_110 field_111]
if field_106 == 1 && reason_fields.all? { |field| attributes[field.to_s].blank? }
@@ -1268,11 +1278,11 @@ private
attributes["ppostcode_full"] = ppostcode_full
attributes["reasonpref"] = field_106
- attributes["rp_homeless"] = field_107
- attributes["rp_insan_unsat"] = field_108
- attributes["rp_medwel"] = field_109
- attributes["rp_hardship"] = field_110
- attributes["rp_dontknow"] = field_111
+ attributes["rp_homeless"] = field_107 unless rp_dontknow_conflict?
+ attributes["rp_insan_unsat"] = field_108 unless rp_dontknow_conflict?
+ attributes["rp_medwel"] = field_109 unless rp_dontknow_conflict?
+ attributes["rp_hardship"] = field_110 unless rp_dontknow_conflict?
+ attributes["rp_dontknow"] = field_111 unless rp_dontknow_conflict?
attributes["cbl"] = cbl
attributes["chr"] = chr
@@ -1666,6 +1676,17 @@ private
end
end
+ def rp_dontknow_conflict?
+ other_reason_fields = %i[field_107 field_108 field_109 field_110]
+ if field_106 == 1
+ selected_reasons = other_reason_fields.select { |field| send(field) == 1 }
+ dont_know_selected = field_111 == 1
+
+ return true if selected_reasons.any? && dont_know_selected
+ end
+ false
+ end
+
def referral_type
mapping = {
1 => [20, 2, 8],
diff --git a/config/locales/validations/lettings/2024/bulk_upload.en.yml b/config/locales/validations/lettings/2024/bulk_upload.en.yml
index 18d051b4d..7431b074a 100644
--- a/config/locales/validations/lettings/2024/bulk_upload.en.yml
+++ b/config/locales/validations/lettings/2024/bulk_upload.en.yml
@@ -58,3 +58,7 @@ en:
invalid: "Select a valid nationality."
charges:
missing_charges: "Please enter the %{sentence_fragment}. If there is no %{sentence_fragment}, please enter '0'."
+ reasonpref:
+ conflict:
+ dont_know: "You cannot select 'Don't know' if any of the other reasonable preference reasons are also selected."
+ other: "You cannot select this reasonable preference reason as you've also selected 'Don't know' as a reason."
diff --git a/config/locales/validations/lettings/2025/bulk_upload.en.yml b/config/locales/validations/lettings/2025/bulk_upload.en.yml
index 7acb0726c..28866de21 100644
--- a/config/locales/validations/lettings/2025/bulk_upload.en.yml
+++ b/config/locales/validations/lettings/2025/bulk_upload.en.yml
@@ -58,3 +58,7 @@ en:
invalid: "Select a valid nationality."
charges:
missing_charges: "Please enter the %{sentence_fragment}. If there is no %{sentence_fragment}, please enter '0'."
+ reasonpref:
+ conflict:
+ dont_know: "You cannot select 'Don't know' if any of the other reasonable preference reasons are also selected."
+ other: "You cannot select this reasonable preference reason as you've also selected 'Don't know' as a reason."
diff --git a/lib/tasks/recalculate_invalid_reasonpref_dontknow.rake b/lib/tasks/recalculate_invalid_reasonpref_dontknow.rake
new file mode 100644
index 000000000..14d387662
--- /dev/null
+++ b/lib/tasks/recalculate_invalid_reasonpref_dontknow.rake
@@ -0,0 +1,12 @@
+desc "Bulk update logs with invalid rp_dontknow values"
+task recalculate_invalid_rpdontknow: :environment do
+ validation_trigger_condition = "rp_dontknow = 1 AND (rp_homeless = 1 OR rp_insan_unsat = 1 OR rp_medwel = 1 OR rp_hardship = 1)"
+
+ LettingsLog.filter_by_year(2024).where(validation_trigger_condition).find_each do |log|
+ log.rp_dontknow = 0
+
+ unless log.save
+ Rails.logger.info "Could not save changes to lettings log #{log.id}"
+ end
+ end
+end
diff --git a/spec/lib/tasks/recalculate_invalid_reasonpref_dontknow_spec.rb b/spec/lib/tasks/recalculate_invalid_reasonpref_dontknow_spec.rb
new file mode 100644
index 000000000..3487f3989
--- /dev/null
+++ b/spec/lib/tasks/recalculate_invalid_reasonpref_dontknow_spec.rb
@@ -0,0 +1,70 @@
+require "rails_helper"
+require "rake"
+
+RSpec.describe "recalculate_invalid_reasonpref_dontknow" do
+ subject(:task) { Rake::Task["recalculate_invalid_rpdontknow"] }
+
+ before do
+ Rake.application.rake_require("tasks/recalculate_invalid_reasonpref_dontknow")
+ Rake::Task.define_task(:environment)
+ task.reenable
+ end
+
+ let(:invalid_logs) { create_list(:lettings_log, 5, :completed, reasonpref: 1, rp_dontknow: 1, rp_homeless: 1, rp_insan_unsat: rand(2), rp_medwel: rand(2), rp_hardship: rand(2), updated_at: Time.zone.local(2024, 4, 2, 12, 0, 0)) }
+ let(:pre_2024_invalid_logs) do
+ create_list(:lettings_log, 5, :completed, reasonpref: 1, rp_dontknow: 1, rp_homeless: 1, rp_insan_unsat: rand(2), rp_medwel: rand(2), rp_hardship: rand(2)).each do |log|
+ log.startdate = Time.zone.local(rand(2021..2023), 4, 1)
+ log.save!(validate: false)
+ end
+ end
+ let(:valid_logs) { create_list(:lettings_log, 3, :completed, reasonpref: 1, rp_dontknow: 0, rp_homeless: 1, rp_insan_unsat: 1, rp_medwel: rand(2), rp_hardship: rand(2), updated_at: Time.zone.local(2024, 4, 2, 12, 0, 0)) }
+
+ it "updates the logs from 2024/25 with invalid rp_dontknow values" do
+ invalid_logs.each do |log|
+ expect(log.reasonpref).to eq(1)
+ expect(log.rp_dontknow).to eq(1)
+ expect(log.rp_homeless).to eq(1)
+ end
+ task.invoke
+ invalid_logs.each do |log|
+ log.reload
+ expect(log.reasonpref).to eq(1)
+ expect(log.rp_dontknow).to eq(0)
+ expect(log.rp_homeless).to eq(1)
+ expect(log.updated_at).not_to eq(Time.zone.local(2024, 4, 2, 12, 0, 0))
+ end
+ end
+
+ it "does not update the logs pre 2024 with invalid rp_dontknow values" do
+ pre_2024_invalid_logs.each do |log|
+ expect(log.reasonpref).to eq(1)
+ expect(log.rp_dontknow).to eq(1)
+ expect(log.rp_homeless).to eq(1)
+ end
+ task.invoke
+ pre_2024_invalid_logs.each do |log|
+ log.reload
+ expect(log.reasonpref).to eq(1)
+ expect(log.rp_dontknow).to eq(1)
+ expect(log.rp_homeless).to eq(1)
+ end
+ end
+
+ it "does not update the logs with valid rp_dontknow values" do
+ valid_logs.each do |log|
+ expect(log.reasonpref).to eq(1)
+ expect(log.rp_dontknow).to eq(0)
+ expect(log.rp_homeless).to eq(1)
+ expect(log.rp_insan_unsat).to eq(1)
+ end
+ task.invoke
+ valid_logs.each do |log|
+ log.reload
+ expect(log.reasonpref).to eq(1)
+ expect(log.rp_dontknow).to eq(0)
+ expect(log.rp_homeless).to eq(1)
+ expect(log.rp_insan_unsat).to eq(1)
+ expect(log.updated_at).to eq(Time.zone.local(2024, 4, 2, 12, 0, 0))
+ end
+ end
+end
diff --git a/spec/services/bulk_upload/lettings/year2024/row_parser_spec.rb b/spec/services/bulk_upload/lettings/year2024/row_parser_spec.rb
index a3392e50d..e4b34ac36 100644
--- a/spec/services/bulk_upload/lettings/year2024/row_parser_spec.rb
+++ b/spec/services/bulk_upload/lettings/year2024/row_parser_spec.rb
@@ -1247,7 +1247,7 @@ RSpec.describe BulkUpload::Lettings::Year2024::RowParser do
end
end
- context "when some reasonable preference options are seleceted" do
+ context "when some reasonable preference options are selected" do
let(:attributes) { setup_section_params.merge({ bulk_upload:, field_106: "1", field_107: "1", field_108: nil, field_109: "1", field_110: nil, field_111: nil }) }
it "sets the rest of the options to 0" do
@@ -1260,7 +1260,7 @@ RSpec.describe BulkUpload::Lettings::Year2024::RowParser do
end
end
- context "when some reasonable preference options are seleceted but reasonpref is No" do
+ context "when some reasonable preference options are selected but reasonpref is No" do
let(:attributes) { setup_section_params.merge({ bulk_upload:, field_106: "2", field_107: "1", field_108: nil, field_109: "1", field_110: nil, field_111: nil }) }
it "sets the options to nil" do
@@ -1285,6 +1285,20 @@ RSpec.describe BulkUpload::Lettings::Year2024::RowParser do
expect(parser.errors[:field_111]).to be_present
end
end
+
+ context "when reasonpref is Yes, some reasonable preferences are selected but also so is 'Don't know'" do
+ let(:attributes) { setup_section_params.merge({ bulk_upload:, field_106: "1", field_107: "1", field_108: "1", field_109: nil, field_110: nil, field_111: "1" }) }
+
+ it "is not permitted" do
+ parser.valid?
+ expect(parser.errors[:field_107]).to be_present
+ expect(parser.errors[:field_108]).to be_present
+ expect(parser.errors[:field_111]).to be_present
+ expect(parser.errors[:field_107]).to include(I18n.t("validations.lettings.2024.bulk_upload.reasonpref.conflict.other"))
+ expect(parser.errors[:field_108]).to include(I18n.t("validations.lettings.2024.bulk_upload.reasonpref.conflict.other"))
+ expect(parser.errors[:field_111]).to include(I18n.t("validations.lettings.2024.bulk_upload.reasonpref.conflict.dont_know"))
+ end
+ end
end
describe "#field_116" do # referral
diff --git a/spec/services/bulk_upload/lettings/year2025/row_parser_spec.rb b/spec/services/bulk_upload/lettings/year2025/row_parser_spec.rb
index a822d6f2a..3f0ef35b9 100644
--- a/spec/services/bulk_upload/lettings/year2025/row_parser_spec.rb
+++ b/spec/services/bulk_upload/lettings/year2025/row_parser_spec.rb
@@ -1096,6 +1096,19 @@ RSpec.describe BulkUpload::Lettings::Year2025::RowParser do
expect(parser.errors[:field_111]).to be_present
end
end
+
+ context "when some reasonable preference options are selected" do
+ let(:attributes) { setup_section_params.merge({ bulk_upload:, field_106: "1", field_107: "1", field_108: nil, field_109: "1", field_110: nil, field_111: nil }) }
+
+ it "sets the rest of the options to 0" do
+ parser.valid?
+ expect(parser.log.rp_homeless).to eq(1)
+ expect(parser.log.rp_insan_unsat).to eq(0)
+ expect(parser.log.rp_medwel).to eq(1)
+ expect(parser.log.rp_hardship).to eq(0)
+ expect(parser.log.rp_dontknow).to eq(0)
+ end
+ end
end
describe "#field_116" do # referral
From 5da13b6b298fc5708f7a1c46da881ccb759d4506 Mon Sep 17 00:00:00 2001
From: Manny Dinssa <44172848+Dinssa@users.noreply.github.com>
Date: Thu, 6 Mar 2025 12:10:36 +0000
Subject: [PATCH 6/6] CLDC-3787: Autocomplete address uprn search (#2967)
* Prototype
* Remove git from dockerfile
* UPRN search too
* Revert address client and use uprn client
* Add address search to lettings too
* Updates with lettings logs
* Update copy
* Move guidance to partial
* Fix uprn return
* Delete new db file, restore old
* Lint
* Remove old db file
* Lint
* Add new db file, remove old
* JS lint
* Update schema
* Add manual entry option
* Update derived variables
* Comment out old version of find address in 2024
* Remove db column
* Add new db columns
* Update guidance partial
* Add unless to migration
* Add migration files to remove and readd
* authenticate user
* Remove file
* Delete migration files
* Add search url
* Add search url
* Fix onConfirm
* Add manual entry button instead of change skip link
* Revert "Add manual entry button instead of change skip link"
This reverts commit 22577c801aca940acfc16caf94d3159071ea8258.
* Revert "Revert "Add manual entry button instead of change skip link""
This reverts commit 9f0a2111a58e933a28105e54aba6ca08c2d043b7.
* Replace uprn question
* Update question copy
* Allow changing the address search value
* Rename address autocomplete to address search
* Add buttons to switch between address questions
* Fix controller logic
* Enable adding question numbers to page headers
* Update skip links
* Add js disabled message to select
* Alternative way to handle js disabled users
* Revert "Alternative way to handle js disabled users"
This reverts commit 10da3d61e2f89ec29ef9f9071c63eb99aa2bb482.
* Fix typo
* Fix address options for address search question
* Reuse AddressDataPresenter where appropriate
* Lint
* Remove uprn selection question tests
* Reuse UprnDataPresenter where appropriate
* CSV export, exclude address_search
* Add address search to sales and lettings factory bots
* Exclude old address questions from routing, keep as exported values
* lint
* Update uprn value
* Add address search input boolean and switch between questions
* Reword copy, remove "Find" and "Search by"
* Align address questions, add question number and question text
* Remove old wip depends on
* Update some tests
* Update migration, move default value from db to model
* Update test
* Remove binding pry
* Lint
* Update test
* Lint
* Update test
* Update routes with underscores
* Remove debugging
* Limit visible logs to user
* Add manual address entry selected variable
* Change address search min length to 3chars
* Remove binding.pry
* Update factory bots, manual_address_entry_selected to true for preexisting tests
* Update model tests
* Update sales model tests excl E-code tests
* Update address search request test
* Reuse uprn id instead of address_search
* Set manual address entry selected as false when creating test logs
* Update model test
* Update request tests and remove old questions
* Add back test
* Update services
* Update more tests
Co-authored-by: kosiakkatrina
* Update request tests
* update model tests
* Also update sales log
* Update service csv uprn_selection values to 1
* Add tests for pages and questions
* Update test
* Update uprn_known
* Lint
* Add feature test
* Update test
* Update tests
* Remove test
* pre-consolidate migration files
* Indentation
* Controller method improvements
* Update question numbers for 2025/26
* Update question numbers tests
* consolidate and delete old migration files
* undo changes to schema.rb
* Update 2025 property information translation files
* Update answer options to show singular previously selected result if present
* Move buttons to bottom guidance partials
* Small improvements, make address search and existing search more similar
* Validate entered addresses as within England
* Update test
* Revert "Validate entered addresses as within England"
This reverts commit 2dbfbcc8a5188cde7fb0ac0dcdbc5919eefd6a12.
* Add missing button to sales address page
* Change error code
* Clear invalid options
* Edit no results message method
* Keep no result logic just change text
* Display uprn value with address value
* Still show no results message when characters entered is less than 3 rather than nothing
* Fix uprn result when query is ambiguous
* Reduce min match for address search
* Hide no result found message just before results are populated
* Prevent changing logs to 2025 with invalid addresses
* Correct attribute name
* Handle nil
* Remove custom error message
* Remove unused variables from factory
* Update tests, remove address and postcode from old find address
* Fix bug clearing uprn from see all answers
* Revert "Fix bug clearing uprn from see all answers"
This reverts commit a66c47a1abf7a429f25e0a016fedb0b92e92f15c.
* Undo changes to validation method
* Fix unchanged uprn_selection when clearing or changing uprn
* Undo a change
* Update bulk upload 2025
* Fix typo
* Remove redundant line
---------
Co-authored-by: Kat <54268893+kosiakkatrina@users.noreply.github.com>
Co-authored-by: kosiakkatrina
---
app/controllers/address_search_controller.rb | 70 ++++
app/controllers/test_data_controller.rb | 8 +-
.../controllers/address_search_controller.js | 73 ++++
app/frontend/controllers/index.js | 3 +
.../lettings_log_variables.rb | 15 +
.../derived_variables/sales_log_variables.rb | 49 ++-
.../form/lettings/pages/address_fallback.rb | 9 +-
.../form/lettings/pages/address_search.rb | 17 +
.../form/lettings/questions/address_search.rb | 44 ++
.../questions/postcode_for_full_address.rb | 1 +
.../subsections/property_information.rb | 6 +-
.../form/sales/pages/address_fallback.rb | 11 +-
app/models/form/sales/pages/address_search.rb | 23 ++
.../form/sales/pages/no_address_found.rb | 1 -
.../form/sales/questions/address_search.rb | 44 ++
.../questions/postcode_for_full_address.rb | 1 +
.../sales/subsections/property_information.rb | 6 +-
app/models/log.rb | 20 +-
app/services/address_client.rb | 7 +-
.../lettings/year2024/row_parser.rb | 1 +
.../lettings/year2025/row_parser.rb | 1 +
.../bulk_upload/sales/year2024/row_parser.rb | 1 +
.../bulk_upload/sales/year2025/row_parser.rb | 1 +
app/services/csv/lettings_log_csv_service.rb | 22 +-
app/services/csv/sales_log_csv_service.rb | 14 +
app/services/uprn_data_presenter.rb | 8 +
.../form/_address_search_question.html.erb | 24 ++
app/views/form/_select_question.html.erb | 21 +-
.../form/guidance/_address_fallback.html.erb | 3 +
.../form/guidance/_address_search.html.erb | 7 +
.../forms/2024/lettings/guidance.en.yml | 11 +-
.../2024/lettings/property_information.en.yml | 7 +
.../locales/forms/2024/sales/guidance.en.yml | 7 +
.../2024/sales/property_information.en.yml | 7 +
.../forms/2025/lettings/guidance.en.yml | 7 +
.../2025/lettings/property_information.en.yml | 45 +--
.../locales/forms/2025/sales/guidance.en.yml | 7 +
.../2025/sales/property_information.en.yml | 45 +--
.../sales/property_information.en.yml | 14 +-
config/routes.rb | 4 +
...d_manual_address_entry_selected_to_logs.rb | 6 +
db/schema.rb | 1 +
spec/factories/lettings_log.rb | 9 +-
spec/factories/sales_log.rb | 10 +-
spec/features/form/address_search_spec.rb | 45 +++
spec/features/form/form_navigation_spec.rb | 60 ---
spec/features/lettings_log_spec.rb | 375 ------------------
spec/features/sales_log_spec.rb | 375 ------------------
.../files/sales_logs_csv_export_codes_24.csv | 2 +-
.../files/sales_logs_csv_export_labels_24.csv | 2 +-
..._logs_csv_export_non_support_labels_24.csv | 2 +-
spec/models/bulk_upload_spec.rb | 4 +-
.../lettings/pages/address_fallback_spec.rb | 9 +-
.../lettings/pages/address_search_spec.rb | 42 ++
.../lettings/questions/address_search_spec.rb | 68 ++++
.../lettings/questions/uprn_selection_spec.rb | 8 +-
.../form/lettings/questions/uprn_spec.rb | 4 +
.../subsections/property_information_spec.rb | 12 +-
.../form/sales/pages/address_fallback_spec.rb | 9 +-
.../form/sales/pages/address_search_spec.rb | 42 ++
.../sales/pages/uprn_confirmation_spec.rb | 4 +
.../sales/questions/address_search_spec.rb | 68 ++++
.../sales/questions/uprn_selection_spec.rb | 8 +-
.../subsections/property_information_spec.rb | 12 +-
spec/models/sales_log_spec.rb | 7 +-
.../sales/property_validations_spec.rb | 4 +-
spec/request_helper.rb | 2 +-
.../address_search_controller_spec.rb | 148 +++++++
.../duplicate_logs_controller_spec.rb | 10 +-
.../csv/sales_log_csv_service_spec.rb | 8 +-
.../lettings_log_export_service_spec.rb | 2 +-
.../shared_examples_for_derived_fields.rb | 13 +-
spec/shared/shared_log_examples.rb | 2 -
73 files changed, 997 insertions(+), 1041 deletions(-)
create mode 100644 app/controllers/address_search_controller.rb
create mode 100644 app/frontend/controllers/address_search_controller.js
create mode 100644 app/models/form/lettings/pages/address_search.rb
create mode 100644 app/models/form/lettings/questions/address_search.rb
create mode 100644 app/models/form/sales/pages/address_search.rb
create mode 100644 app/models/form/sales/questions/address_search.rb
create mode 100644 app/views/form/_address_search_question.html.erb
create mode 100644 app/views/form/guidance/_address_fallback.html.erb
create mode 100644 app/views/form/guidance/_address_search.html.erb
create mode 100644 db/migrate/20250219122817_add_manual_address_entry_selected_to_logs.rb
create mode 100644 spec/features/form/address_search_spec.rb
create mode 100644 spec/models/form/lettings/pages/address_search_spec.rb
create mode 100644 spec/models/form/lettings/questions/address_search_spec.rb
create mode 100644 spec/models/form/sales/pages/address_search_spec.rb
create mode 100644 spec/models/form/sales/questions/address_search_spec.rb
create mode 100644 spec/requests/address_search_controller_spec.rb
diff --git a/app/controllers/address_search_controller.rb b/app/controllers/address_search_controller.rb
new file mode 100644
index 000000000..616d5b702
--- /dev/null
+++ b/app/controllers/address_search_controller.rb
@@ -0,0 +1,70 @@
+class AddressSearchController < ApplicationController
+ before_action :authenticate_user!
+ before_action :set_log, only: %i[manual_input search_input]
+
+ def index
+ query = params[:query]
+
+ if query.match?(/\A\d+\z/) && query.length > 5
+ # Query is all numbers and greater than 5 digits, assume it's a UPRN
+ service = UprnClient.new(query)
+ service.call
+
+ if service.error.present?
+ render json: { error: service.error }, status: :not_found
+ else
+ presenter = UprnDataPresenter.new(service.result)
+ render json: [{ text: presenter.address, value: presenter.uprn }]
+ end
+ elsif query.match?(/[a-zA-Z]/)
+ # Query contains letters, assume it's an address
+ service = AddressClient.new(query, { minmatch: 0.2 })
+ service.call
+
+ if service.error.present?
+ render json: { error: service.error }, status: :not_found
+ else
+ results = service.result.map do |result|
+ presenter = AddressDataPresenter.new(result)
+ { text: presenter.address, value: presenter.uprn }
+ end
+ render json: results
+ end
+ else
+ # Query is ambiguous, use both APIs and merge results
+ address_service = AddressClient.new(query, { minmatch: 0.2 })
+ uprn_service = UprnClient.new(query)
+
+ address_service.call
+ uprn_service.call
+
+ results = ([uprn_service.result] || []) + (address_service.result || [])
+
+ if address_service.error.present? && uprn_service.error.present?
+ render json: { error: "Address and UPRN are not recognised." }, status: :not_found
+ else
+ formatted_results = results.map do |result|
+ presenter = AddressDataPresenter.new(result)
+ { text: presenter.address, value: presenter.uprn }
+ end
+ render json: formatted_results
+ end
+ end
+ end
+
+ def manual_input
+ @log.update!(manual_address_entry_selected: true)
+ redirect_to polymorphic_url([@log, :address])
+ end
+
+ def search_input
+ @log.update!(manual_address_entry_selected: false)
+ redirect_to polymorphic_url([@log, :address_search])
+ end
+
+private
+
+ def set_log
+ @log = current_user.send("#{params[:log_type]}s").find(params[:log_id])
+ end
+end
diff --git a/app/controllers/test_data_controller.rb b/app/controllers/test_data_controller.rb
index 9195b77aa..8617ff3b5 100644
--- a/app/controllers/test_data_controller.rb
+++ b/app/controllers/test_data_controller.rb
@@ -4,14 +4,14 @@ class TestDataController < ApplicationController
def create_test_lettings_log
return render_not_found unless FeatureToggle.create_test_logs_enabled?
- log = FactoryBot.create(:lettings_log, :completed, assigned_to: current_user, ppostcode_full: "SW1A 1AA")
+ log = FactoryBot.create(:lettings_log, :completed, assigned_to: current_user, ppostcode_full: "SW1A 1AA", manual_address_entry_selected: false)
redirect_to lettings_log_path(log)
end
def create_setup_test_lettings_log
return render_not_found unless FeatureToggle.create_test_logs_enabled?
- log = FactoryBot.create(:lettings_log, :setup_completed, assigned_to: current_user)
+ log = FactoryBot.create(:lettings_log, :setup_completed, assigned_to: current_user, manual_address_entry_selected: false)
redirect_to lettings_log_path(log)
end
@@ -40,14 +40,14 @@ class TestDataController < ApplicationController
def create_test_sales_log
return render_not_found unless FeatureToggle.create_test_logs_enabled?
- log = FactoryBot.create(:sales_log, :completed, assigned_to: current_user)
+ log = FactoryBot.create(:sales_log, :completed, assigned_to: current_user, manual_address_entry_selected: false)
redirect_to sales_log_path(log)
end
def create_setup_test_sales_log
return render_not_found unless FeatureToggle.create_test_logs_enabled?
- log = FactoryBot.create(:sales_log, :shared_ownership_setup_complete, assigned_to: current_user)
+ log = FactoryBot.create(:sales_log, :shared_ownership_setup_complete, assigned_to: current_user, manual_address_entry_selected: false)
redirect_to sales_log_path(log)
end
diff --git a/app/frontend/controllers/address_search_controller.js b/app/frontend/controllers/address_search_controller.js
new file mode 100644
index 000000000..de54090ec
--- /dev/null
+++ b/app/frontend/controllers/address_search_controller.js
@@ -0,0 +1,73 @@
+import { Controller } from '@hotwired/stimulus'
+import accessibleAutocomplete from 'accessible-autocomplete'
+import 'accessible-autocomplete/dist/accessible-autocomplete.min.css'
+
+const options = []
+
+const fetchOptions = async (query, searchUrl) => {
+ if (query.length < 2) {
+ throw new Error('Query must be at least 2 characters long.')
+ }
+ try {
+ const response = await fetch(`${searchUrl}?query=${encodeURIComponent(query.trim())}`)
+ return await response.json()
+ } catch (error) {
+ return error
+ }
+}
+
+const fetchAndPopulateSearchResults = async (query, populateResults, searchUrl, populateOptions, selectEl) => {
+ if (/\S/.test(query)) {
+ try {
+ const results = await fetchOptions(query, searchUrl)
+ if (results.length === 0) {
+ populateOptions([], selectEl)
+ populateResults([])
+ } else {
+ populateOptions(results, selectEl)
+ populateResults(Object.values(results).map((o) => `${o.text} (${o.value})`))
+ }
+ } catch (error) {
+ populateOptions([], selectEl)
+ populateResults([])
+ }
+ }
+}
+
+const populateOptions = (results, selectEl) => {
+ selectEl.innerHTML = ''
+
+ results.forEach((result) => {
+ const option = document.createElement('option')
+ option.value = result.value
+ option.innerHTML = `${result.text} (${result.value})`
+ selectEl.appendChild(option)
+ options.push(option)
+ })
+}
+
+export default class extends Controller {
+ connect () {
+ const searchUrl = JSON.parse(this.element.dataset.info).search_url
+ const selectEl = this.element
+
+ accessibleAutocomplete.enhanceSelectElement({
+ defaultValue: '',
+ selectElement: selectEl,
+ minLength: 2,
+ source: (query, populateResults) => {
+ fetchAndPopulateSearchResults(query, populateResults, searchUrl, populateOptions, selectEl)
+ },
+ autoselect: true,
+ showNoOptionsFound: true,
+ placeholder: 'Start typing to search',
+ templates: { suggestion: (value) => value },
+ onConfirm: (val) => {
+ const selectedResult = Array.from(selectEl.options).find(option => option.text === val)
+ if (selectedResult) {
+ selectedResult.selected = true
+ }
+ }
+ })
+ }
+}
diff --git a/app/frontend/controllers/index.js b/app/frontend/controllers/index.js
index 944e32e2d..fa7944045 100644
--- a/app/frontend/controllers/index.js
+++ b/app/frontend/controllers/index.js
@@ -19,6 +19,8 @@ import FilterLayoutController from './filter_layout_controller.js'
import TabsController from './tabs_controller.js'
+import AddressSearchController from './address_search_controller.js'
+
application.register('accessible-autocomplete', AccessibleAutocompleteController)
application.register('conditional-filter', ConditionalFilterController)
application.register('conditional-question', ConditionalQuestionController)
@@ -27,3 +29,4 @@ application.register('numeric-question', NumericQuestionController)
application.register('filter-layout', FilterLayoutController)
application.register('search', SearchController)
application.register('tabs', TabsController)
+application.register('address-search', AddressSearchController)
diff --git a/app/models/derived_variables/lettings_log_variables.rb b/app/models/derived_variables/lettings_log_variables.rb
index 4eaa5dbff..8cabf1ce5 100644
--- a/app/models/derived_variables/lettings_log_variables.rb
+++ b/app/models/derived_variables/lettings_log_variables.rb
@@ -113,6 +113,21 @@ module DerivedVariables::LettingsLogVariables
self.previous_la_known = nil if is_renewal?
end
+ if form.start_year_2024_or_later?
+ if manual_address_entry_selected
+ self.uprn_known = 0
+ self.uprn_selection = nil
+ self.uprn_confirmed = nil
+ else
+ self.uprn_confirmed = 1 if uprn.present?
+ self.uprn_known = 1 if uprn.present?
+ reset_address_fields! if uprn.blank?
+ if uprn_changed?
+ self.uprn_selection = uprn
+ end
+ end
+ end
+
if is_renewal?
self.underoccupation_benefitcap = 2 if collection_start_year == 2021
self.voiddate = startdate
diff --git a/app/models/derived_variables/sales_log_variables.rb b/app/models/derived_variables/sales_log_variables.rb
index ff8cd4916..04658c222 100644
--- a/app/models/derived_variables/sales_log_variables.rb
+++ b/app/models/derived_variables/sales_log_variables.rb
@@ -55,27 +55,29 @@ module DerivedVariables::SalesLogVariables
if uprn_known&.zero?
self.uprn = nil
if uprn_known_was == 1
- self.address_line1 = nil
- self.address_line2 = nil
- self.town_or_city = nil
- self.county = nil
- self.pcodenk = nil
- self.postcode_full = nil
- self.la = nil
+ reset_address_fields!
end
end
if uprn_known == 1 && uprn_confirmed&.zero?
- self.uprn = nil
+ reset_address_fields!
self.uprn_known = 0
self.uprn_confirmed = nil
- self.address_line1 = nil
- self.address_line2 = nil
- self.town_or_city = nil
- self.county = nil
- self.pcodenk = nil
- self.postcode_full = nil
- self.la = nil
+ end
+
+ if form.start_year_2024_or_later?
+ if manual_address_entry_selected
+ self.uprn_known = 0
+ self.uprn_selection = nil
+ self.uprn_confirmed = nil
+ else
+ self.uprn_confirmed = 1 if uprn.present?
+ self.uprn_known = 1 if uprn.present?
+ reset_address_fields! if uprn.blank?
+ if uprn_changed?
+ self.uprn_selection = uprn
+ end
+ end
end
if form.start_year_2025_or_later? && is_bedsit?
@@ -248,4 +250,21 @@ private
def prevten_was_social_housing?
[1, 2].include?(prevten) || [1, 2].include?(prevtenbuy2)
end
+
+ def reset_address_fields!
+ self.uprn = nil
+ self.uprn_known = nil
+ self.address_line1 = nil
+ self.address_line2 = nil
+ self.town_or_city = nil
+ self.county = nil
+ self.pcode1 = nil
+ self.pcode2 = nil
+ self.pcodenk = nil
+ self.address_line1_input = nil
+ self.postcode_full_input = nil
+ self.postcode_full = nil
+ self.is_la_inferred = nil
+ self.la = nil
+ end
end
diff --git a/app/models/form/lettings/pages/address_fallback.rb b/app/models/form/lettings/pages/address_fallback.rb
index fd580a3ed..f7503e3af 100644
--- a/app/models/form/lettings/pages/address_fallback.rb
+++ b/app/models/form/lettings/pages/address_fallback.rb
@@ -3,14 +3,7 @@ class Form::Lettings::Pages::AddressFallback < ::Form::Page
super
@id = "address"
@copy_key = "lettings.property_information.address"
- @depends_on = [
- { "is_supported_housing?" => false, "uprn_known" => nil, "uprn_selection" => "uprn_not_listed" },
- { "is_supported_housing?" => false, "uprn_known" => 0, "uprn_selection" => "uprn_not_listed" },
- { "is_supported_housing?" => false, "uprn_confirmed" => 0, "uprn_selection" => "uprn_not_listed" },
- { "is_supported_housing?" => false, "uprn_known" => nil, "address_options_present?" => false },
- { "is_supported_housing?" => false, "uprn_known" => 0, "address_options_present?" => false },
- { "is_supported_housing?" => false, "uprn_confirmed" => 0, "address_options_present?" => false },
- ]
+ @depends_on = [{ "is_supported_housing?" => false, "manual_address_entry_selected" => true }]
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
diff --git a/app/models/form/lettings/pages/address_search.rb b/app/models/form/lettings/pages/address_search.rb
new file mode 100644
index 000000000..866018d45
--- /dev/null
+++ b/app/models/form/lettings/pages/address_search.rb
@@ -0,0 +1,17 @@
+class Form::Lettings::Pages::AddressSearch < ::Form::Page
+ def initialize(id, hsh, subsection)
+ super
+ @id = "address_search"
+ @copy_key = "sales.property_information.address_search"
+ @depends_on = [{ "is_supported_housing?" => false, "manual_address_entry_selected" => false }]
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ end
+
+ def questions
+ @questions ||= [
+ Form::Lettings::Questions::AddressSearch.new(nil, nil, self),
+ ]
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2024 => 12, 2025 => 16 }.freeze
+end
diff --git a/app/models/form/lettings/questions/address_search.rb b/app/models/form/lettings/questions/address_search.rb
new file mode 100644
index 000000000..ed7edf894
--- /dev/null
+++ b/app/models/form/lettings/questions/address_search.rb
@@ -0,0 +1,44 @@
+class Form::Lettings::Questions::AddressSearch < ::Form::Question
+ def initialize(id, hsh, page)
+ super
+ @id = "uprn"
+ @type = "address_search"
+ @copy_key = "lettings.property_information.address_search"
+ @plain_label = true
+ @bottom_guidance_partial = "address_search"
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ @hide_question_number_on_page = true
+ end
+
+ def answer_options(log = nil, _user = nil)
+ return {} unless ActiveRecord::Base.connected?
+ return {} unless log&.address_options&.any?
+
+ log.address_options.each_with_object({}) do |option, hash|
+ hash[option[:uprn]] = { "value" => "#{option[:address]} (#{option[:uprn]})" }
+ end
+ end
+
+ def get_extra_check_answer_value(log)
+ return unless log.uprn_known == 1
+
+ value = [
+ log.address_line1,
+ log.address_line2,
+ log.town_or_city,
+ log.county,
+ log.postcode_full,
+ (LocalAuthority.find_by(code: log.la)&.name if log.la.present?),
+ ].select(&:present?)
+
+ return unless value.any?
+
+ "\n\n#{value.join("\n")}"
+ end
+
+ def displayed_answer_options(log, user = nil)
+ answer_options(log, user).transform_values { |value| value["value"] } || {}
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2024 => 12, 2025 => 16 }.freeze
+end
diff --git a/app/models/form/lettings/questions/postcode_for_full_address.rb b/app/models/form/lettings/questions/postcode_for_full_address.rb
index a4c775a55..114cf0db5 100644
--- a/app/models/form/lettings/questions/postcode_for_full_address.rb
+++ b/app/models/form/lettings/questions/postcode_for_full_address.rb
@@ -20,6 +20,7 @@ class Form::Lettings::Questions::PostcodeForFullAddress < ::Form::Question
@disable_clearing_if_not_routed_or_dynamic_answer_options = true
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
@hide_question_number_on_page = true
+ @bottom_guidance_partial = "address_fallback"
end
QUESTION_NUMBER_FROM_YEAR = { 2023 => 12, 2024 => 13, 2025 => 17 }.freeze
diff --git a/app/models/form/lettings/subsections/property_information.rb b/app/models/form/lettings/subsections/property_information.rb
index d5005b142..475ff0a8c 100644
--- a/app/models/form/lettings/subsections/property_information.rb
+++ b/app/models/form/lettings/subsections/property_information.rb
@@ -30,11 +30,7 @@ class Form::Lettings::Subsections::PropertyInformation < ::Form::Subsection
def uprn_questions
if form.start_year_2024_or_later?
[
- Form::Lettings::Pages::Uprn.new(nil, nil, self),
- Form::Lettings::Pages::UprnConfirmation.new(nil, nil, self),
- Form::Lettings::Pages::AddressMatcher.new(nil, nil, self),
- Form::Lettings::Pages::NoAddressFound.new(nil, nil, self), # soft validation
- Form::Lettings::Pages::UprnSelection.new(nil, nil, self),
+ Form::Lettings::Pages::AddressSearch.new(nil, nil, self),
Form::Lettings::Pages::AddressFallback.new(nil, nil, self),
]
else
diff --git a/app/models/form/sales/pages/address_fallback.rb b/app/models/form/sales/pages/address_fallback.rb
index b6818ae0c..9465a494f 100644
--- a/app/models/form/sales/pages/address_fallback.rb
+++ b/app/models/form/sales/pages/address_fallback.rb
@@ -3,14 +3,7 @@ class Form::Sales::Pages::AddressFallback < ::Form::Page
super
@id = "address"
@copy_key = "sales.property_information.address"
- @depends_on = [
- { "uprn_known" => nil, "uprn_selection" => "uprn_not_listed" },
- { "uprn_known" => 0, "uprn_selection" => "uprn_not_listed" },
- { "uprn_confirmed" => 0, "uprn_selection" => "uprn_not_listed" },
- { "uprn_known" => nil, "address_options_present?" => false },
- { "uprn_known" => 0, "address_options_present?" => false },
- { "uprn_confirmed" => 0, "address_options_present?" => false },
- ]
+ @depends_on = [{ "manual_address_entry_selected" => true }]
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
end
@@ -24,5 +17,5 @@ class Form::Sales::Pages::AddressFallback < ::Form::Page
]
end
- QUESTION_NUMBER_FROM_YEAR = { 2024 => 16, 2025 => 16 }.freeze
+ QUESTION_NUMBER_FROM_YEAR = { 2024 => 16, 2025 => 14 }.freeze
end
diff --git a/app/models/form/sales/pages/address_search.rb b/app/models/form/sales/pages/address_search.rb
new file mode 100644
index 000000000..f0d58af58
--- /dev/null
+++ b/app/models/form/sales/pages/address_search.rb
@@ -0,0 +1,23 @@
+class Form::Sales::Pages::AddressSearch < ::Form::Page
+ def initialize(id, hsh, subsection)
+ super
+ @id = "address_search"
+ @copy_key = "sales.property_information.address_search"
+ @depends_on = [{ "manual_address_entry_selected" => false }]
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ end
+
+ def questions
+ @questions ||= [
+ Form::Sales::Questions::AddressSearch.new(nil, nil, self),
+ ]
+ end
+
+ def skip_href(log = nil)
+ return unless log
+
+ "/#{log.log_type.dasherize}s/#{log.id}/property-number-of-bedrooms"
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2024 => 15, 2025 => 13 }.freeze
+end
diff --git a/app/models/form/sales/pages/no_address_found.rb b/app/models/form/sales/pages/no_address_found.rb
index ae2663896..e0ff5bcb2 100644
--- a/app/models/form/sales/pages/no_address_found.rb
+++ b/app/models/form/sales/pages/no_address_found.rb
@@ -16,7 +16,6 @@ class Form::Sales::Pages::NoAddressFound < ::Form::Page
{ "uprn_known" => nil, "address_options_present?" => false },
{ "uprn_known" => 0, "address_options_present?" => false },
{ "uprn_confirmed" => 0, "address_options_present?" => false },
-
]
end
diff --git a/app/models/form/sales/questions/address_search.rb b/app/models/form/sales/questions/address_search.rb
new file mode 100644
index 000000000..d6acbaba1
--- /dev/null
+++ b/app/models/form/sales/questions/address_search.rb
@@ -0,0 +1,44 @@
+class Form::Sales::Questions::AddressSearch < ::Form::Question
+ def initialize(id, hsh, page)
+ super
+ @id = "uprn"
+ @type = "address_search"
+ @copy_key = "sales.property_information.address_search"
+ @plain_label = true
+ @bottom_guidance_partial = "address_search"
+ @question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
+ @hide_question_number_on_page = true
+ end
+
+ def answer_options(log = nil, _user = nil)
+ return {} unless ActiveRecord::Base.connected?
+ return {} unless log&.address_options&.any?
+
+ log.address_options.each_with_object({}) do |option, hash|
+ hash[option[:uprn]] = { "value" => "#{option[:address]} (#{option[:uprn]})" }
+ end
+ end
+
+ def get_extra_check_answer_value(log)
+ return unless log.uprn_known == 1
+
+ value = [
+ log.address_line1,
+ log.address_line2,
+ log.town_or_city,
+ log.county,
+ log.postcode_full,
+ (LocalAuthority.find_by(code: log.la)&.name if log.la.present?),
+ ].select(&:present?)
+
+ return unless value.any?
+
+ "\n\n#{value.join("\n")}"
+ end
+
+ def displayed_answer_options(log, user = nil)
+ answer_options(log, user).transform_values { |value| value["value"] } || {}
+ end
+
+ QUESTION_NUMBER_FROM_YEAR = { 2024 => 15, 2025 => 13 }.freeze
+end
diff --git a/app/models/form/sales/questions/postcode_for_full_address.rb b/app/models/form/sales/questions/postcode_for_full_address.rb
index 95656a108..e99ec108b 100644
--- a/app/models/form/sales/questions/postcode_for_full_address.rb
+++ b/app/models/form/sales/questions/postcode_for_full_address.rb
@@ -20,6 +20,7 @@ class Form::Sales::Questions::PostcodeForFullAddress < ::Form::Question
@disable_clearing_if_not_routed_or_dynamic_answer_options = true
@question_number = QUESTION_NUMBER_FROM_YEAR[form.start_date.year] || QUESTION_NUMBER_FROM_YEAR[QUESTION_NUMBER_FROM_YEAR.keys.max]
@hide_question_number_on_page = true
+ @bottom_guidance_partial = "address_fallback"
end
QUESTION_NUMBER_FROM_YEAR = { 2023 => 15, 2024 => 16, 2025 => 14 }.freeze
diff --git a/app/models/form/sales/subsections/property_information.rb b/app/models/form/sales/subsections/property_information.rb
index 28c0ad004..e33666208 100644
--- a/app/models/form/sales/subsections/property_information.rb
+++ b/app/models/form/sales/subsections/property_information.rb
@@ -24,11 +24,7 @@ class Form::Sales::Subsections::PropertyInformation < ::Form::Subsection
def uprn_questions
if form.start_year_2024_or_later?
[
- Form::Sales::Pages::Uprn.new(nil, nil, self),
- Form::Sales::Pages::UprnConfirmation.new(nil, nil, self),
- Form::Sales::Pages::AddressMatcher.new(nil, nil, self),
- Form::Sales::Pages::NoAddressFound.new(nil, nil, self),
- Form::Sales::Pages::UprnSelection.new(nil, nil, self),
+ Form::Sales::Pages::AddressSearch.new(nil, nil, self),
Form::Sales::Pages::AddressFallback.new(nil, nil, self),
Form::Sales::Pages::PropertyLocalAuthority.new(nil, nil, self),
Form::Sales::Pages::Buyer1IncomeDiscountedMaxValueCheck.new("local_authority_buyer_1_income_max_value_check", nil, self, check_answers_card_number: nil),
diff --git a/app/models/log.rb b/app/models/log.rb
index d55289997..1454aef65 100644
--- a/app/models/log.rb
+++ b/app/models/log.rb
@@ -75,8 +75,7 @@ class Log < ApplicationRecord
presenter = UprnDataPresenter.new(service.result)
self.uprn_known = 1
- self.uprn_confirmed = nil unless skip_update_uprn_confirmed
- self.uprn_selection = nil
+ self.uprn_selection = uprn
self.address_line1 = presenter.address_line1
self.address_line2 = presenter.address_line2
self.town_or_city = presenter.town_or_city
@@ -126,16 +125,27 @@ class Log < ApplicationRecord
end
def address_options
- return @address_options if @address_options && @last_searched_address_string == address_string
+ if uprn.present?
+ service = UprnClient.new(uprn)
+ service.call
+ if service.result.blank? || service.error.present?
+ @address_options = []
+ return @address_options
+ end
+
+ presenter = UprnDataPresenter.new(service.result)
+ @address_options = [{ address: presenter.address, uprn: presenter.uprn }]
+ else
+ return @address_options if @address_options && @last_searched_address_string == address_string
+ return if address_string.blank?
- if [address_line1_input, postcode_full_input].all?(&:present?)
@last_searched_address_string = address_string
service = AddressClient.new(address_string)
service.call
if service.result.blank? || service.error.present?
@address_options = []
- return @answer_options
+ return @address_options
end
address_opts = []
diff --git a/app/services/address_client.rb b/app/services/address_client.rb
index 81c8da7ed..20cf603fe 100644
--- a/app/services/address_client.rb
+++ b/app/services/address_client.rb
@@ -7,8 +7,9 @@ class AddressClient
ADDRESS = "api.os.uk".freeze
PATH = "/search/places/v1/find".freeze
- def initialize(address)
+ def initialize(address, options = {})
@address = address
+ @options = options
end
def call
@@ -43,8 +44,8 @@ private
params = {
query: address,
key: ENV["OS_DATA_KEY"],
- maxresults: 10,
- minmatch: 0.4,
+ maxresults: @options[:maxresults] || 10,
+ minmatch: @options[:minmatch] || 0.4,
}
uri.query = URI.encode_www_form(params)
uri.to_s
diff --git a/app/services/bulk_upload/lettings/year2024/row_parser.rb b/app/services/bulk_upload/lettings/year2024/row_parser.rb
index 2b3aae5d5..20eb4dccd 100644
--- a/app/services/bulk_upload/lettings/year2024/row_parser.rb
+++ b/app/services/bulk_upload/lettings/year2024/row_parser.rb
@@ -1363,6 +1363,7 @@ private
attributes["address_line1_input"] = address_line1_input
attributes["postcode_full_input"] = postcode_full
attributes["select_best_address_match"] = true if field_16.blank?
+ attributes["manual_address_entry_selected"] = field_16.blank?
end
attributes
diff --git a/app/services/bulk_upload/lettings/year2025/row_parser.rb b/app/services/bulk_upload/lettings/year2025/row_parser.rb
index 522960aa1..1f4a80f9b 100644
--- a/app/services/bulk_upload/lettings/year2025/row_parser.rb
+++ b/app/services/bulk_upload/lettings/year2025/row_parser.rb
@@ -1360,6 +1360,7 @@ private
attributes["address_line1_input"] = address_line1_input
attributes["postcode_full_input"] = postcode_full
attributes["select_best_address_match"] = true if field_18.blank?
+ attributes["manual_address_entry_selected"] = field_18.blank?
end
attributes
diff --git a/app/services/bulk_upload/sales/year2024/row_parser.rb b/app/services/bulk_upload/sales/year2024/row_parser.rb
index f33bfb5fa..6bf1cc4be 100644
--- a/app/services/bulk_upload/sales/year2024/row_parser.rb
+++ b/app/services/bulk_upload/sales/year2024/row_parser.rb
@@ -986,6 +986,7 @@ private
attributes["address_line1_input"] = address_line1_input
attributes["postcode_full_input"] = postcode_full
attributes["select_best_address_match"] = true if field_22.blank?
+ attributes["manual_address_entry_selected"] = field_22.blank?
attributes["ethnic_group2"] = infer_buyer2_ethnic_group_from_ethnic
attributes["ethnicbuy2"] = field_40
diff --git a/app/services/bulk_upload/sales/year2025/row_parser.rb b/app/services/bulk_upload/sales/year2025/row_parser.rb
index ee97d6776..f6a2a6e1a 100644
--- a/app/services/bulk_upload/sales/year2025/row_parser.rb
+++ b/app/services/bulk_upload/sales/year2025/row_parser.rb
@@ -961,6 +961,7 @@ private
attributes["address_line1_input"] = address_line1_input
attributes["postcode_full_input"] = postcode_full
attributes["select_best_address_match"] = true if field_16.blank?
+ attributes["manual_address_entry_selected"] = field_16.blank?
attributes["ethnic_group2"] = infer_buyer2_ethnic_group_from_ethnic
attributes["ethnicbuy2"] = field_37
diff --git a/app/services/csv/lettings_log_csv_service.rb b/app/services/csv/lettings_log_csv_service.rb
index 3c4324d14..0a187d524 100644
--- a/app/services/csv/lettings_log_csv_service.rb
+++ b/app/services/csv/lettings_log_csv_service.rb
@@ -208,6 +208,11 @@ module Csv
3 => "Intermediate Rent",
}.freeze
+ UPRN_KNOWN_LABELS = {
+ 0 => "No",
+ 1 => "Yes",
+ }.freeze
+
LABELS = {
"lettype" => LETTYPE_LABELS,
"irproduct" => IRPRODUCT_LABELS,
@@ -215,6 +220,7 @@ module Csv
"newprop" => NEWPROP_LABELS,
"incref" => INCREF_LABELS,
"renttype" => RENTTYPE_LABELS,
+ "uprn_known" => UPRN_KNOWN_LABELS,
}.freeze
CONVENTIONAL_YES_NO_ATTRIBUTES = %w[illness_type_1 illness_type_2 illness_type_3 illness_type_4 illness_type_5 illness_type_6 illness_type_7 illness_type_8 illness_type_9 illness_type_10 refused cbl cap chr accessible_register letting_allocation_none housingneeds_a housingneeds_b housingneeds_c housingneeds_d housingneeds_e housingneeds_f housingneeds_g housingneeds_h has_benefits nocharge postcode_known].freeze
@@ -249,6 +255,18 @@ module Csv
"letting_allocation_unknown" => %w[letting_allocation_none],
}.freeze
+ ATTRIBUTE_MAPPINGS_2024 = {
+ "uprn" => %w[uprn_known uprn],
+ }.freeze
+
+ def attribute_mappings
+ if @year >= 2024
+ ATTRIBUTE_MAPPINGS.merge(ATTRIBUTE_MAPPINGS_2024)
+ else
+ ATTRIBUTE_MAPPINGS
+ end
+ end
+
ORDERED_ADDRESS_FIELDS = %w[uprn address_line1 address_line2 town_or_city county postcode_full is_la_inferred la_label la uprn_known uprn_selection address_search_value_check address_line1_input postcode_full_input address_line1_as_entered address_line2_as_entered town_or_city_as_entered county_as_entered postcode_full_as_entered la_as_entered].freeze
SUPPORT_ONLY_ATTRIBUTES = %w[postcode_known is_la_inferred totchild totelder totadult net_income_known previous_la_known is_previous_la_inferred age1_known age2_known age3_known age4_known age5_known age6_known age7_known age8_known details_known_2 details_known_3 details_known_4 details_known_5 details_known_6 details_known_7 details_known_8 wrent wscharge wpschrge wsupchrg wtcharge wtshortfall old_form_id old_id tshortfall_known hhtype la prevloc updated_by_id uprn_confirmed address_line1_input postcode_full_input uprn_selection address_line1_as_entered address_line2_as_entered town_or_city_as_entered county_as_entered postcode_full_as_entered la_as_entered created_by].freeze
@@ -279,10 +297,10 @@ module Csv
ordered_questions.flat_map do |question|
if question.type == "checkbox"
question.answer_options.keys.reject { |key| key == "divider" }.map { |key|
- ATTRIBUTE_MAPPINGS.fetch(key, key)
+ attribute_mappings.fetch(key, key)
}.flatten
else
- ATTRIBUTE_MAPPINGS.fetch(question.id, question.id)
+ attribute_mappings.fetch(question.id, question.id)
end
end
end
diff --git a/app/services/csv/sales_log_csv_service.rb b/app/services/csv/sales_log_csv_service.rb
index f74684868..08ce178e3 100644
--- a/app/services/csv/sales_log_csv_service.rb
+++ b/app/services/csv/sales_log_csv_service.rb
@@ -152,6 +152,15 @@ module Csv
"uprn_confirmed" => "UPRNCONFIRMED",
}.freeze
+ UPRN_CONFIRMED_LABELS = {
+ 0 => "No",
+ 1 => "Yes",
+ }.freeze
+
+ LABELS = {
+ "uprn_confirmed" => UPRN_CONFIRMED_LABELS,
+ }.freeze
+
def formatted_attribute_headers
return @attributes unless @user.support?
@@ -208,6 +217,9 @@ module Csv
unless @user.support? && @year >= 2024
mappings["postcode_full"] = %w[pcode1 pcode2]
end
+ if @year >= 2024
+ mappings["uprn"] = %w[uprn uprn_confirmed address_line1_input postcode_full_input uprn_selection]
+ end
mappings
end
@@ -280,6 +292,8 @@ module Csv
end
def get_label(value, attribute, log)
+ return LABELS[attribute][value] if LABELS.key?(attribute)
+
log.form
.get_question(attribute, log)
&.label_from_value(value)
diff --git a/app/services/uprn_data_presenter.rb b/app/services/uprn_data_presenter.rb
index 7c70a81e3..049afb1b4 100644
--- a/app/services/uprn_data_presenter.rb
+++ b/app/services/uprn_data_presenter.rb
@@ -55,4 +55,12 @@ class UprnDataPresenter
def result_from_lpi?
data["LPI_KEY"].present?
end
+
+ def uprn
+ data["UPRN"]
+ end
+
+ def address
+ data["ADDRESS"]
+ end
end
diff --git a/app/views/form/_address_search_question.html.erb b/app/views/form/_address_search_question.html.erb
new file mode 100644
index 000000000..ea30be718
--- /dev/null
+++ b/app/views/form/_address_search_question.html.erb
@@ -0,0 +1,24 @@
+<% selected = @log.public_send(question.id) || "" %>
+<% answers = question.displayed_answer_options(@log, current_user).map { |key, value| OpenStruct.new(id: key, name: select_option_name(value), resource: value) } %>
+<%= render partial: "form/guidance/#{question.top_guidance_partial}" if question.top_guidance? %>
+
+<%= f.govuk_select(question.id.to_sym,
+ label: legend(question, page_header, conditional),
+ "data-controller": "address-search",
+ "data-info": { search_url: address_search_url }.to_json,
+ caption: caption(caption_text, page_header, conditional),
+ hint: { text: question.hint_text&.html_safe }) do %>
+ <% if answers.any? %>
+ <% answers.each do |answer| %>
+
+ <% end %>
+ <% else %>
+
+ <% end %>
+<% end %>
+
+<%= render partial: "form/guidance/#{question.bottom_guidance_partial}" if question.bottom_guidance? %>
diff --git a/app/views/form/_select_question.html.erb b/app/views/form/_select_question.html.erb
index 2dceffd63..7a3b19c32 100644
--- a/app/views/form/_select_question.html.erb
+++ b/app/views/form/_select_question.html.erb
@@ -1,20 +1,23 @@
-
<% selected = @log.public_send(question.id) || "" %>
<% answers = question.displayed_answer_options(@log, current_user).map { |key, value| OpenStruct.new(id: key, name: select_option_name(value), resource: value) } %>
<%= render partial: "form/guidance/#{question.top_guidance_partial}" if question.top_guidance? %>
<%= f.govuk_select(question.id.to_sym,
- label: legend(question, page_header, conditional),
- "data-controller": "accessible-autocomplete",
- caption: caption(caption_text, page_header, conditional),
- hint: { text: question.hint_text&.html_safe }) do %>
+ label: legend(question, page_header, conditional),
+ "data-controller": "accessible-autocomplete",
+ caption: caption(caption_text, page_header, conditional),
+ hint: { text: question.hint_text&.html_safe }) do %>
+ <% if answers.any? %>
<% answers.each do |answer| %>
+ data-synonyms="<%= answer_option_synonyms(answer.resource) %>"
+ data-append="<%= answer_option_append(answer.resource) %>"
+ data-hint="<%= answer_option_hint(answer.resource) %>"
+ <%= question.answer_selected?(@log, answer) ? "selected" : "" %>><%= answer.name || answer.resource %>
<% end %>
+ <% else %>
+
<% end %>
+<% end %>
<%= render partial: "form/guidance/#{question.bottom_guidance_partial}" if question.bottom_guidance? %>
diff --git a/app/views/form/guidance/_address_fallback.html.erb b/app/views/form/guidance/_address_fallback.html.erb
new file mode 100644
index 000000000..4ee0bd608
--- /dev/null
+++ b/app/views/form/guidance/_address_fallback.html.erb
@@ -0,0 +1,3 @@
+
If your organisation’s schemes were migrated from old CORE, they may have new names and codes. Search by postcode to find your scheme.
"
scheme_changes_link_text: "Read more about how schemes have changed"
view_schemes_link_text: "View your organisation’s schemes"
-
+
privacy_notice_tenant:
content: "Make sure the lead tenant has seen or been given access to %{privacy_notice_link} before completing this log. This is a legal requirement under data protection legislation."
privacy_notice_link_text: "the Ministry of Housing, Communities and Local Government (MHCLG) privacy notice"
@@ -60,4 +60,11 @@ en:
housing benefit
child benefit
council tax support
- "
\ No newline at end of file
+ "
+
+ address_search:
+ title: "Can’t find the address you’re looking for?"
+ content: "
+
Some properties may not be available yet e.g. new builds; you might need to enter them manually instead
+
For UPRN (Unique Property Reference Number), please enter the full value exactly
+
"
diff --git a/config/locales/forms/2024/lettings/property_information.en.yml b/config/locales/forms/2024/lettings/property_information.en.yml
index 9e7326040..016c78958 100644
--- a/config/locales/forms/2024/lettings/property_information.en.yml
+++ b/config/locales/forms/2024/lettings/property_information.en.yml
@@ -50,6 +50,13 @@ en:
hint_text: ""
question_text: "Select the correct address"
+ address_search:
+ page_header: "What is the property's address?"
+ check_answer_label: "Address"
+ check_answer_prompt: "Enter address or UPRN"
+ hint_text: "For example, '1 Victoria Road' or '10010457355'"
+ question_text: "Enter address or UPRN"
+
address:
page_header: "What is the property's address?"
address_line1:
diff --git a/config/locales/forms/2024/sales/guidance.en.yml b/config/locales/forms/2024/sales/guidance.en.yml
index 801c43a5c..b57595c66 100644
--- a/config/locales/forms/2024/sales/guidance.en.yml
+++ b/config/locales/forms/2024/sales/guidance.en.yml
@@ -44,3 +44,10 @@ en:
privacy_notice_buyer:
content: "Make sure the buyer has seen or been given access to %{privacy_notice_link} before completing this log. This is a legal requirement under data protection legislation."
privacy_notice_link_text: "the Ministry of Housing, Communities and Local Government (MHCLG) privacy notice"
+
+ address_search:
+ title: "Can’t find the address you’re looking for?"
+ content: "
+
Some properties may not be available yet e.g. new builds; you might need to enter them manually instead
+
For UPRN (Unique Property Reference Number), please enter the full value exactly
+
"
diff --git a/config/locales/forms/2024/sales/property_information.en.yml b/config/locales/forms/2024/sales/property_information.en.yml
index b40e40267..518654211 100644
--- a/config/locales/forms/2024/sales/property_information.en.yml
+++ b/config/locales/forms/2024/sales/property_information.en.yml
@@ -43,6 +43,13 @@ en:
hint_text: ""
question_text: "Select the correct address"
+ address_search:
+ page_header: "What is the property's address?"
+ check_answer_label: "Address"
+ check_answer_prompt: "Enter address or UPRN"
+ hint_text: "For example, '1 Victoria Road' or '10010457355'"
+ question_text: "Enter address or UPRN"
+
address:
page_header: "What is the property's address?"
address_line1:
diff --git a/config/locales/forms/2025/lettings/guidance.en.yml b/config/locales/forms/2025/lettings/guidance.en.yml
index 340eb11d5..cb51fbf9d 100644
--- a/config/locales/forms/2025/lettings/guidance.en.yml
+++ b/config/locales/forms/2025/lettings/guidance.en.yml
@@ -61,3 +61,10 @@ en:
Some properties may not be available yet e.g. new builds; you might need to enter them manually instead
+
For UPRN (Unique Property Reference Number), please enter the full value exactly
+
"
diff --git a/config/locales/forms/2025/lettings/property_information.en.yml b/config/locales/forms/2025/lettings/property_information.en.yml
index 22a0d12db..41cf2d3aa 100644
--- a/config/locales/forms/2025/lettings/property_information.en.yml
+++ b/config/locales/forms/2025/lettings/property_information.en.yml
@@ -10,45 +10,12 @@ en:
hint_text: ""
question_text: "Is this the first time the property has been let as social housing?"
- uprn:
- page_header: ""
- uprn_known:
- check_answer_label: "UPRN known"
- check_answer_prompt: "Enter UPRN if known"
- hint_text: "The Unique Property Reference Number (UPRN) is a unique number system created by Ordnance Survey and used by housing providers and various industries across the UK. An example UPRN is 10010457355.
The UPRN may not be the same as the property reference assigned by your organisation.
If you don’t know the UPRN you can enter the address of the property instead on the next screen."
- question_text: "Do you know the property's UPRN?"
- uprn:
- check_answer_label: "UPRN"
- check_answer_prompt: ""
- hint_text: ""
- question_text: "What is the property's UPRN?"
-
- uprn_confirmed:
- page_header: "We found an address that might be this property"
- check_answer_label: "Is this the right address?"
- check_answer_prompt: "Tell us if this is the right address"
- hint_text: ""
- question_text: "Is this the property address?"
-
- address_matcher:
- page_header: "Find an address"
- address_line1_input:
- check_answer_label: "Find address"
- check_answer_prompt: "Try find address"
- hint_text: ""
- question_text: "Address line 1"
- postcode_full_input:
- check_answer_label: ""
- check_answer_prompt: ""
- hint_text: ""
- question_text: "Postcode"
-
- uprn_selection:
- page_header: "We found an address that might be this property"
- check_answer_label: "Select correct address"
- check_answer_prompt: "Select correct address"
- hint_text: ""
- question_text: "Select the correct address"
+ address_search:
+ page_header: "What is the property's address?"
+ check_answer_label: "Address"
+ check_answer_prompt: "Enter address or UPRN"
+ hint_text: "For example, '1 Victoria Road' or '10010457355'"
+ question_text: "Enter address or UPRN"
address:
page_header: "What is the property's address?"
diff --git a/config/locales/forms/2025/sales/guidance.en.yml b/config/locales/forms/2025/sales/guidance.en.yml
index 4ed6796b3..cfb9b0615 100644
--- a/config/locales/forms/2025/sales/guidance.en.yml
+++ b/config/locales/forms/2025/sales/guidance.en.yml
@@ -44,3 +44,10 @@ en:
privacy_notice_buyer:
content: "Make sure the buyer has seen or been given access to %{privacy_notice_link} before completing this log. This is a legal requirement under data protection legislation."
privacy_notice_link_text: "the Ministry of Housing, Communities and Local Government (MHCLG) privacy notice"
+
+ address_search:
+ title: "Can’t find the address you’re looking for?"
+ content: "
+
Some properties may not be available yet e.g. new builds; you might need to enter them manually instead
+
For UPRN (Unique Property Reference Number), please enter the full value exactly
+
"
diff --git a/config/locales/forms/2025/sales/property_information.en.yml b/config/locales/forms/2025/sales/property_information.en.yml
index 332219a6b..e91089bc5 100644
--- a/config/locales/forms/2025/sales/property_information.en.yml
+++ b/config/locales/forms/2025/sales/property_information.en.yml
@@ -3,45 +3,12 @@ en:
2025:
sales:
property_information:
- uprn:
- page_header: ""
- uprn_known:
- check_answer_label: "UPRN known"
- check_answer_prompt: "Enter UPRN if known"
- hint_text: "The Unique Property Reference Number (UPRN) is a unique number system created by Ordnance Survey and used by housing providers and various industries across the UK. An example UPRN is 10010457355.
The UPRN may not be the same as the property reference assigned by your organisation.
If you don’t know the UPRN you can enter the address of the property instead on the next screen."
- question_text: "Do you know the property's UPRN?"
- uprn:
- check_answer_label: "UPRN"
- check_answer_prompt: ""
- hint_text: ""
- question_text: "What is the property's UPRN?"
-
- uprn_confirmed:
- page_header: "We found an address that might be this property"
- check_answer_label: "Is this the right address?"
- check_answer_prompt: "Tell us if this is the right address"
- hint_text: ""
- question_text: "Is this the property address?"
-
- address_matcher:
- page_header: "Find an address"
- address_line1_input:
- check_answer_label: "Find address"
- check_answer_prompt: "Try find address"
- hint_text: ""
- question_text: "Address line 1"
- postcode_full_input:
- check_answer_label: ""
- check_answer_prompt: ""
- hint_text: ""
- question_text: "Postcode"
-
- uprn_selection:
- page_header: "We found an address that might be this property"
- check_answer_label: "Select correct address"
- check_answer_prompt: "Select correct address"
- hint_text: ""
- question_text: "Select the correct address"
+ address_search:
+ page_header: "What is the property's address?"
+ check_answer_label: "Address"
+ check_answer_prompt: "Enter address or UPRN"
+ hint_text: "For example, '1 Victoria Road' or '10010457355'"
+ question_text: "Enter address or UPRN"
address:
page_header: "What is the property's address?"
diff --git a/config/locales/validations/sales/property_information.en.yml b/config/locales/validations/sales/property_information.en.yml
index 9014f1d78..f421177af 100644
--- a/config/locales/validations/sales/property_information.en.yml
+++ b/config/locales/validations/sales/property_information.en.yml
@@ -7,7 +7,7 @@ en:
joint_purchase: "Buyers’ last accommodation and discounted ownership postcodes must match."
not_joint_purchase: "Buyer’s last accommodation and discounted ownership postcodes must match."
invalid: "Enter a postcode in the correct format, for example AA1 1AA."
- not_in_england: "It looks like you have entered a postcode outside of England - only submit Lettings forms for Lettings that occur in England"
+ not_in_england: "It looks like you have entered a postcode outside of England. Only create logs for sales in England."
ppostcode_full:
postcode_must_match_previous:
joint_purchase: "Buyers’ last accommodation and discounted ownership postcodes must match."
@@ -21,7 +21,7 @@ en:
joint_purchase: "Buyers’ last accommodation and discounted ownership postcodes must match."
not_joint_purchase: "Buyer’s last accommodation and discounted ownership postcodes must match."
invalid: "UPRN must be 12 digits or less."
- not_in_england: "It looks like you have an entered a postcode outside of England. Only create logs for lettings in England."
+ not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
beds:
bedsits_have_max_one_bedroom: "Number of bedrooms must be 1 if the property is a bedsit."
proptype:
@@ -29,11 +29,11 @@ en:
uprn_known:
invalid: "You must answer UPRN known?"
la:
- not_in_england: "It looks like you have entered an address outside of England. Only create logs for lettings in England."
+ not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
uprn_confirmation:
- not_in_england: "It looks like you have entered an address outside of England. Only create logs for lettings in England."
+ not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
uprn_selection:
- not_in_england: "It looks like you have entered an address outside of England. Only create logs for lettings in England."
+ not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
saledate:
- postcode_not_in_england: "It looks like you have an entered a postcode outside of England. Only create logs for lettings in England."
- address_not_in_england: "It looks like you have entered an address outside of England. Only create logs for lettings in England."
+ postcode_not_in_england: "It looks like you have entered a postcode outside of England. Only create logs for sales in England."
+ address_not_in_england: "It looks like you have entered an address outside of England. Only create logs for sales in England."
diff --git a/config/routes.rb b/config/routes.rb
index 471c89578..304d54ef0 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -39,6 +39,10 @@ Rails.application.routes.draw do
get "/data-sharing-agreement", to: "content#data_sharing_agreement"
get "/service-moved", to: "maintenance#service_moved"
get "/service-unavailable", to: "maintenance#service_unavailable"
+ get "/address-search", to: "address_search#index"
+ get "/address-search/current", to: "address_search#current"
+ get "/address-search/manual-input/:log_type/:log_id", to: "address_search#manual_input", as: "address_manual_input"
+ get "/address-search/search-input/:log_type/:log_id", to: "address_search#search_input", as: "address_search_input"
get "collection-resources", to: "collection_resources#index"
get "/collection-resources/:log_type/:year/:resource_type/download", to: "collection_resources#download_mandatory_collection_resource", as: :download_mandatory_collection_resource
diff --git a/db/migrate/20250219122817_add_manual_address_entry_selected_to_logs.rb b/db/migrate/20250219122817_add_manual_address_entry_selected_to_logs.rb
new file mode 100644
index 000000000..a0d0f7529
--- /dev/null
+++ b/db/migrate/20250219122817_add_manual_address_entry_selected_to_logs.rb
@@ -0,0 +1,6 @@
+class AddManualAddressEntrySelectedToLogs < ActiveRecord::Migration[7.2]
+ def change
+ add_column :sales_logs, :manual_address_entry_selected, :boolean, default: false
+ add_column :lettings_logs, :manual_address_entry_selected, :boolean, default: false
+ end
+end
diff --git a/db/schema.rb b/db/schema.rb
index 20a836eed..82d67b432 100644
--- a/db/schema.rb
+++ b/db/schema.rb
@@ -771,6 +771,7 @@ ActiveRecord::Schema[7.2].define(version: 2025_02_25_180643) do
t.decimal "mrentprestaircasing", precision: 10, scale: 2
t.datetime "lasttransaction"
t.datetime "initialpurchase"
+ t.boolean "manual_address_entry_selected", default: false
t.index ["assigned_to_id"], name: "index_sales_logs_on_assigned_to_id"
t.index ["bulk_upload_id"], name: "index_sales_logs_on_bulk_upload_id"
t.index ["created_by_id"], name: "index_sales_logs_on_created_by_id"
diff --git a/spec/factories/lettings_log.rb b/spec/factories/lettings_log.rb
index 5d13cacfa..ad81bca5d 100644
--- a/spec/factories/lettings_log.rb
+++ b/spec/factories/lettings_log.rb
@@ -6,6 +6,7 @@ FactoryBot.define do
managing_organisation { assigned_to.organisation }
created_at { Time.zone.today }
updated_at { Time.zone.today }
+ manual_address_entry_selected { true }
before(:create) do |log, _evaluator|
if log.period && !log.managing_organisation.organisation_rent_periods.exists?(rent_period: log.period)
@@ -167,13 +168,11 @@ FactoryBot.define do
town_or_city { Faker::Address.city }
ppcodenk { 1 }
tshortfall_known { 1 }
- after(:build) do |log, _evaluator|
+ after(:build) do |log, evaluator|
if log.startdate >= Time.zone.local(2024, 4, 1)
- log.address_line1_input = log.address_line1
- log.postcode_full_input = log.postcode_full
log.nationality_all_group = 826
- log.uprn = "10033558653"
- log.uprn_selection = 1
+ log.uprn = evaluator.uprn || "10033558653"
+ log.uprn_selection = evaluator.uprn_selection || "10033558653"
end
end
end
diff --git a/spec/factories/sales_log.rb b/spec/factories/sales_log.rb
index 820c99fdc..64137704c 100644
--- a/spec/factories/sales_log.rb
+++ b/spec/factories/sales_log.rb
@@ -8,6 +8,8 @@ FactoryBot.define do
managing_organisation { assigned_to.organisation }
created_at { Time.zone.now }
updated_at { Time.zone.now }
+ manual_address_entry_selected { true }
+
trait :in_progress do
purchid { "PC123" }
ownershipsch { 2 }
@@ -166,14 +168,12 @@ FactoryBot.define do
nationalbuy2 { 13 }
buy2living { 3 }
proplen_asked { 1 }
- after(:build) do |log, _evaluator|
+ after(:build) do |log, evaluator|
if log.saledate >= Time.zone.local(2024, 4, 1)
- log.address_line1_input = log.address_line1
- log.postcode_full_input = log.postcode_full
log.nationality_all_group = 826
log.nationality_all_buyer2_group = 826
- log.uprn = "10033558653"
- log.uprn_selection = 1
+ log.uprn = evaluator.uprn || "10033558653"
+ log.uprn_selection = evaluator.uprn_selection || "10033558653"
end
if log.saledate >= Time.zone.local(2025, 4, 1)
log.relat2 = "X" if log.relat2 == "C"
diff --git a/spec/features/form/address_search_spec.rb b/spec/features/form/address_search_spec.rb
new file mode 100644
index 000000000..cd1738195
--- /dev/null
+++ b/spec/features/form/address_search_spec.rb
@@ -0,0 +1,45 @@
+require "rails_helper"
+require_relative "helpers"
+
+RSpec.describe "Address Search" do
+ include Helpers
+ let(:user) { FactoryBot.create(:user) }
+ let(:sales_log) do
+ FactoryBot.create(
+ :sales_log,
+ :shared_ownership_setup_complete,
+ assigned_to: user,
+ manual_address_entry_selected: false,
+ )
+ end
+
+ before do
+ sign_in user
+ end
+
+ context "when using address search feature" do
+ before do
+ visit("/sales-logs/#{sales_log.id}/address-search")
+ end
+
+ it "allows searching by a UPRN", js: true do
+ find("#sales-log-uprn-field").click.native.send_keys("1", "0", "0", "3", "3", "5", "4", "4", "6", "1", "4", :down)
+ expect(find("#sales-log-uprn-field").value).to eq("10033544614")
+ end
+
+ it "allows searching by address", js: true do
+ find("#sales-log-uprn-field").click.native.send_keys("S", "W", "1", "5", :down, :enter)
+ expect(find("#sales-log-uprn-field").value).to eq("SW15")
+ end
+
+ it "displays the placeholder text", js: true do
+ expect(find("#sales-log-uprn-field")["placeholder"]).to eq("Start typing to search")
+ end
+
+ it "displays correct bottom guidance text" do
+ find("span.govuk-details__summary-text", text: "Can’t find the address you’re looking for?").click
+ expect(page).to have_content("Some properties may not be available yet e.g. new builds; you might need to enter them manually instead")
+ expect(page).to have_content("For UPRN (Unique Property Reference Number), please enter the full value exactly")
+ end
+ end
+end
diff --git a/spec/features/form/form_navigation_spec.rb b/spec/features/form/form_navigation_spec.rb
index 6484fe94c..695115a78 100644
--- a/spec/features/form/form_navigation_spec.rb
+++ b/spec/features/form/form_navigation_spec.rb
@@ -186,64 +186,4 @@ RSpec.describe "Form Navigation" do
expect(page).to have_current_path("/lettings-logs/#{id}/duplicate-logs?original_log_id=#{id}")
end
end
-
- describe "searching for an address" do
- let(:now) { Time.zone.local(2024, 5, 1) }
-
- context "with a lettings log" do
- let(:lettings_log) { create(:lettings_log, :setup_completed, startdate: Time.zone.local(2024, 5, 5), assigned_to: user) }
-
- before do
- stub_request(:get, /api\.os\.uk/)
- .to_return(status: 200, body: { results: [{ DPA: { MATCH: 0.9, BUILDING_NAME: "result address line 1", POST_TOWN: "result town or city", POSTCODE: "AA1 1AA", UPRN: "12345" } }] }.to_json, headers: {})
- end
-
- it "allows searching for an address" do
- visit("lettings-logs/#{id}/address-matcher")
- fill_in("lettings-log-address-line1-input-field", with: "address")
- fill_in("lettings-log-postcode-full-input-field", with: "A1 1AA")
- click_button(text: "Search")
- expect(page).to have_current_path("/lettings-logs/#{id}/uprn-selection")
- end
-
- it "allows searching for an address from check your answers page" do
- visit("lettings-logs/#{id}/address-matcher?referrer=check_answers")
- fill_in("lettings-log-address-line1-input-field", with: "address")
- fill_in("lettings-log-postcode-full-input-field", with: "A1 1AA")
- click_button(text: "Search")
- expect(page).to have_current_path("/lettings-logs/#{id}/uprn-selection?referrer=check_answers&unanswered_pages=property_local_authority")
- choose("lettings-log-uprn-selection-12345-field", allow_label_click: true)
- click_button(text: "Save changes")
- expect(page).to have_current_path("/lettings-logs/#{id}/property-information/check-answers")
- end
- end
-
- context "with a sales log" do
- let(:sales_log) { create(:sales_log, :outright_sale_setup_complete, saledate: Time.zone.local(2024, 5, 5), assigned_to: user) }
-
- before do
- stub_request(:get, /api\.os\.uk/)
- .to_return(status: 200, body: { results: [{ DPA: { MATCH: 0.9, BUILDING_NAME: "result address line 1", POST_TOWN: "result town or city", POSTCODE: "AA1 1AA", UPRN: "12345" } }] }.to_json, headers: {})
- end
-
- it "allows searching for an address" do
- visit("sales-logs/#{sales_log.id}/address-matcher")
- fill_in("sales-log-address-line1-input-field", with: "address")
- fill_in("sales-log-postcode-full-input-field", with: "A1 1AA")
- click_button(text: "Search")
- expect(page).to have_current_path("/sales-logs/#{sales_log.id}/uprn-selection")
- end
-
- it "allows searching for an address from check your answers page" do
- visit("sales-logs/#{sales_log.id}/address-matcher?referrer=check_answers")
- fill_in("sales-log-address-line1-input-field", with: "address")
- fill_in("sales-log-postcode-full-input-field", with: "A1 1AA")
- click_button(text: "Search")
- expect(page).to have_current_path("/sales-logs/#{sales_log.id}/uprn-selection?referrer=check_answers&unanswered_pages=property_local_authority")
- choose("sales-log-uprn-selection-12345-field", allow_label_click: true)
- click_button(text: "Save changes")
- expect(page).to have_current_path("/sales-logs/#{sales_log.id}/property-information/check-answers")
- end
- end
- end
end
diff --git a/spec/features/lettings_log_spec.rb b/spec/features/lettings_log_spec.rb
index a400ef2d0..15d24e5ed 100644
--- a/spec/features/lettings_log_spec.rb
+++ b/spec/features/lettings_log_spec.rb
@@ -729,380 +729,5 @@ RSpec.describe "Lettings Log Features" do
expect(duplicate_log.duplicate_set_id).to be_nil
end
end
-
- context "when filling out address fields" do
- let(:lettings_log) { create(:lettings_log, :setup_completed, assigned_to: user) }
-
- before do
- body = {
- results: [
- {
- DPA: {
- "POSTCODE": "AA1 1AA",
- "POST_TOWN": "Bristol",
- "ORGANISATION_NAME": "Some place",
- },
- },
- ],
- }.to_json
-
- WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/uprn?dataset=DPA,LPI&key=OS_DATA_KEY&uprn=111")
- .to_return(status: 200, body:, headers: {})
-
- body = { results: [{ DPA: { UPRN: "111" } }] }.to_json
- WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?query=Address+line+1%2C+AA1+1AA&key=OS_DATA_KEY&maxresults=10&minmatch=0.4")
- .to_return(status: 200, body:, headers: {})
-
- WebMock.stub_request(:get, "https://api.postcodes.io/postcodes/AA11AA")
- .to_return(status: 200, body: "{\"status\":200,\"result\":{\"postcode\":\"AA1 1AA\",\"admin_district\":\"Westminster\",\"codes\":{\"admin_district\":\"E09000033\"}}}", headers: {})
-
- WebMock.stub_request(:get, "https://api.postcodes.io/postcodes/AA12AA")
- .to_return(status: 200, body: "{\"status\":200,\"result\":{\"postcode\":\"AA1 2AA\",\"admin_district\":\"Wigan\",\"codes\":{\"admin_district\":\"E08000010\"}}}", headers: {})
-
- body = { results: [] }.to_json
- WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?query=Address+line+1%2C+AA1+1AB&key=OS_DATA_KEY&maxresults=10&minmatch=0.4")
- .to_return(status: 200, body:, headers: {})
-
- visit("/lettings-logs/#{lettings_log.id}/uprn")
- end
-
- context "and uprn is known and answered" do
- before do
- choose "Yes"
- fill_in("lettings_log[uprn]", with: "111")
- click_button("Save and continue")
- end
-
- context "and uprn is confirmed" do
- it "sets correct address fields" do
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(1) # yes
- expect(lettings_log.uprn).to eq("111")
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(1)
- expect(lettings_log.postcode_full).to eq("AA1 1AA")
- expect(lettings_log.address_line1).to eq("Some Place")
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq("Bristol")
- expect(lettings_log.address_line1_input).to eq(nil)
- expect(lettings_log.postcode_full_input).to eq(nil)
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq("E09000033")
-
- choose "Yes"
- click_button("Save and continue")
-
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(1) # yes
- expect(lettings_log.uprn).to eq("111")
- expect(lettings_log.uprn_confirmed).to eq(1) # yes
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(1)
- expect(lettings_log.postcode_full).to eq("AA1 1AA")
- expect(lettings_log.address_line1).to eq("Some Place")
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq("Bristol")
- expect(lettings_log.address_line1_input).to eq(nil)
- expect(lettings_log.postcode_full_input).to eq(nil)
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq("E09000033")
- end
-
- context "and changes to uprn not known" do
- it "sets correct address fields" do
- visit("/lettings-logs/#{lettings_log.id}/uprn")
-
- choose "No"
- click_button("Save and continue")
-
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(0) # no
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(nil)
- expect(lettings_log.postcode_full).to eq(nil)
- expect(lettings_log.address_line1).to eq(nil)
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.address_line1_input).to eq(nil)
- expect(lettings_log.postcode_full_input).to eq(nil)
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq(nil)
- end
- end
- end
-
- context "and uprn is not confirmed" do
- before do
- choose "No, I want to search for the address instead"
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- lettings_log.reload
-
- expect(lettings_log.uprn_known).to eq(0) # no
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(nil)
- expect(lettings_log.postcode_full).to eq(nil)
- expect(lettings_log.address_line1).to eq(nil)
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.address_line1_input).to eq(nil)
- expect(lettings_log.postcode_full_input).to eq(nil)
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq(nil)
- end
- end
- end
-
- context "and uprn is not known" do
- before do
- choose "No"
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(0) # no
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(nil)
- expect(lettings_log.postcode_full).to eq(nil)
- expect(lettings_log.address_line1).to eq(nil)
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.address_line1_input).to eq(nil)
- expect(lettings_log.postcode_full_input).to eq(nil)
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq(nil)
- end
-
- context "and the address is not found" do
- it "sets correct address fields" do
- fill_in("lettings_log[address_line1_input]", with: "Address line 1")
- fill_in("lettings_log[postcode_full_input]", with: "AA1 1AB")
- click_button("Search")
-
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(0) # no
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(nil)
- expect(lettings_log.postcode_full).to eq(nil)
- expect(lettings_log.address_line1).to eq(nil)
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.address_line1_input).to eq("Address line 1")
- expect(lettings_log.postcode_full_input).to eq("AA1 1AB")
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq(nil)
-
- click_button("Confirm and continue")
-
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(0) # no
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(nil)
- expect(lettings_log.postcode_full).to eq(nil)
- expect(lettings_log.address_line1).to eq(nil)
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.address_line1_input).to eq("Address line 1")
- expect(lettings_log.postcode_full_input).to eq("AA1 1AB")
- expect(lettings_log.address_search_value_check).to eq(0)
- expect(lettings_log.la).to eq(nil)
- end
- end
-
- context "and address is found, re-searched and not found" do
- before do
- fill_in("lettings_log[address_line1_input]", with: "Address line 1")
- fill_in("lettings_log[postcode_full_input]", with: "AA1 1AA")
- click_button("Search")
- visit("/lettings-logs/#{lettings_log.id}/address-matcher")
-
- fill_in("lettings_log[address_line1_input]", with: "Address line 1")
- fill_in("lettings_log[postcode_full_input]", with: "AA1 1AB")
- click_button("Search")
- end
-
- it "routes to the correct page" do
- expect(page).to have_current_path("/lettings-logs/#{lettings_log.id}/no-address-found")
- end
- end
-
- context "and the user selects 'address_not_listed'" do
- before do
- fill_in("lettings_log[address_line1_input]", with: "Address line 1")
- fill_in("lettings_log[postcode_full_input]", with: "AA1 1AA")
- click_button("Search")
- choose "The address is not listed, I want to enter the address manually"
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(0) # no
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq("uprn_not_listed")
- expect(lettings_log.postcode_known).to eq(1)
- expect(lettings_log.postcode_full).to eq("AA1 1AA")
- expect(lettings_log.address_line1).to eq("Address line 1")
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.address_line1_input).to eq("Address line 1")
- expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq("E09000033")
- end
-
- context "and the user enters a new address manually" do
- context "without changing a valid postcode" do
- before do
- fill_in("lettings_log[town_or_city]", with: "Town")
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(0) # no
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq("uprn_not_listed")
- expect(lettings_log.postcode_known).to eq(1)
- expect(lettings_log.postcode_full).to eq("AA1 1AA")
- expect(lettings_log.address_line1).to eq("Address line 1")
- expect(lettings_log.address_line2).to eq("")
- expect(lettings_log.town_or_city).to eq("Town")
- expect(lettings_log.address_line1_input).to eq("Address line 1")
- expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq("E09000033")
- end
- end
-
- context "with changing the postcode" do
- before do
- fill_in("lettings_log[town_or_city]", with: "Town")
- fill_in("lettings_log[postcode_full]", with: "AA12AA")
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(0) # no
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq("uprn_not_listed")
- expect(lettings_log.postcode_known).to eq(1)
- expect(lettings_log.postcode_full).to eq("AA1 2AA")
- expect(lettings_log.address_line1).to eq("Address line 1")
- expect(lettings_log.address_line2).to eq("")
- expect(lettings_log.town_or_city).to eq("Town")
- expect(lettings_log.address_line1_input).to eq("Address line 1")
- expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq("E08000010")
- end
- end
- end
- end
-
- context "and the user selects 'address_not_listed' when partial postcode is entered" do
- before do
- fill_in("lettings_log[address_line1_input]", with: "Address line 1")
- fill_in("lettings_log[postcode_full_input]", with: "AA1")
- click_button("Search")
- choose "The address is not listed, I want to enter the address manually"
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(0) # no
- expect(lettings_log.uprn).to eq(nil)
- expect(lettings_log.uprn_confirmed).to eq(nil)
- expect(lettings_log.uprn_selection).to eq("uprn_not_listed")
- expect(lettings_log.postcode_known).to eq(nil)
- expect(lettings_log.postcode_full).to eq(nil)
- expect(lettings_log.address_line1).to eq("Address line 1")
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq(nil)
- expect(lettings_log.address_line1_input).to eq("Address line 1")
- expect(lettings_log.postcode_full_input).to eq("AA1")
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq(nil)
- end
- end
-
- context "and the user selects 'address_not_listed' and then changes their mind and selects an address" do
- before do
- fill_in("lettings_log[address_line1_input]", with: "Address line 1")
- fill_in("lettings_log[postcode_full_input]", with: "AA1 1AA")
- click_button("Search")
- choose "The address is not listed, I want to enter the address manually"
- click_button("Save and continue")
-
- visit("/lettings-logs/#{lettings_log.id}/uprn-selection")
- choose("lettings-log-uprn-selection-111-field", allow_label_click: true)
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(1)
- expect(lettings_log.uprn).to eq("111")
- expect(lettings_log.uprn_confirmed).to eq(1)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(1)
- expect(lettings_log.postcode_full).to eq("AA1 1AA")
- expect(lettings_log.address_line1).to eq("Some Place")
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq("Bristol")
- expect(lettings_log.address_line1_input).to eq("Address line 1")
- expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq("E09000033")
- end
- end
-
- context "and possible addresses found and selected" do
- before do
- fill_in("lettings_log[address_line1_input]", with: "Address line 1")
- fill_in("lettings_log[postcode_full_input]", with: "AA1 1AA")
- click_button("Search")
- choose("lettings-log-uprn-selection-111-field", allow_label_click: true)
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- lettings_log.reload
- expect(lettings_log.uprn_known).to eq(1)
- expect(lettings_log.uprn).to eq("111")
- expect(lettings_log.uprn_confirmed).to eq(1)
- expect(lettings_log.uprn_selection).to eq(nil)
- expect(lettings_log.postcode_known).to eq(1)
- expect(lettings_log.postcode_full).to eq("AA1 1AA")
- expect(lettings_log.address_line1).to eq("Some Place")
- expect(lettings_log.address_line2).to eq(nil)
- expect(lettings_log.town_or_city).to eq("Bristol")
- expect(lettings_log.address_line1_input).to eq("Address line 1")
- expect(lettings_log.postcode_full_input).to eq("AA1 1AA")
- expect(lettings_log.address_search_value_check).to eq(nil)
- expect(lettings_log.la).to eq("E09000033")
- end
- end
- end
- end
end
end
diff --git a/spec/features/sales_log_spec.rb b/spec/features/sales_log_spec.rb
index 3030d6d6a..3fa89a504 100644
--- a/spec/features/sales_log_spec.rb
+++ b/spec/features/sales_log_spec.rb
@@ -334,381 +334,6 @@ RSpec.describe "Sales Log Features" do
expect(page).to have_current_path("/sales-logs/bulk-uploads")
end
end
-
- context "when filling out address fields" do
- let(:sales_log) { create(:sales_log, :shared_ownership_setup_complete, assigned_to: user) }
-
- before do
- body = {
- results: [
- {
- DPA: {
- "POSTCODE": "AA1 1AA",
- "POST_TOWN": "Bristol",
- "ORGANISATION_NAME": "Some place",
- },
- },
- ],
- }.to_json
-
- WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/uprn?dataset=DPA,LPI&key=OS_DATA_KEY&uprn=111")
- .to_return(status: 200, body:, headers: {})
-
- body = { results: [{ DPA: { UPRN: "111" } }] }.to_json
- WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?query=Address+line+1%2C+AA1+1AA&key=OS_DATA_KEY&maxresults=10&minmatch=0.4")
- .to_return(status: 200, body:, headers: {})
-
- WebMock.stub_request(:get, "https://api.postcodes.io/postcodes/AA11AA")
- .to_return(status: 200, body: "{\"status\":200,\"result\":{\"postcode\":\"AA1 1AA\",\"admin_district\":\"Westminster\",\"codes\":{\"admin_district\":\"E09000033\"}}}", headers: {})
-
- WebMock.stub_request(:get, "https://api.postcodes.io/postcodes/AA12AA")
- .to_return(status: 200, body: "{\"status\":200,\"result\":{\"postcode\":\"AA1 2AA\",\"admin_district\":\"Wigan\",\"codes\":{\"admin_district\":\"E08000010\"}}}", headers: {})
-
- body = { results: [] }.to_json
- WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?query=Address+line+1%2C+AA1+1AB&key=OS_DATA_KEY&maxresults=10&minmatch=0.4")
- .to_return(status: 200, body:, headers: {})
-
- visit("/sales-logs/#{sales_log.id}/uprn")
- end
-
- context "and uprn is known and answered" do
- before do
- choose "Yes"
- fill_in("sales_log[uprn]", with: "111")
- click_button("Save and continue")
- end
-
- context "and uprn is confirmed" do
- it "sets correct address fields" do
- sales_log.reload
- expect(sales_log.uprn_known).to eq(1) # yes
- expect(sales_log.uprn).to eq("111")
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(0)
- expect(sales_log.postcode_full).to eq("AA1 1AA")
- expect(sales_log.address_line1).to eq("Some Place")
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq("Bristol")
- expect(sales_log.address_line1_input).to eq(nil)
- expect(sales_log.postcode_full_input).to eq(nil)
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq("E09000033")
-
- choose "Yes"
- click_button("Save and continue")
-
- sales_log.reload
- expect(sales_log.uprn_known).to eq(1) # yes
- expect(sales_log.uprn).to eq("111")
- expect(sales_log.uprn_confirmed).to eq(1) # yes
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(0)
- expect(sales_log.postcode_full).to eq("AA1 1AA")
- expect(sales_log.address_line1).to eq("Some Place")
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq("Bristol")
- expect(sales_log.address_line1_input).to eq(nil)
- expect(sales_log.postcode_full_input).to eq(nil)
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq("E09000033")
- end
-
- context "and changes to uprn not known" do
- it "sets correct address fields" do
- visit("/sales-logs/#{sales_log.id}/uprn")
-
- choose "No"
- click_button("Save and continue")
-
- sales_log.reload
- expect(sales_log.uprn_known).to eq(0) # no
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(nil)
- expect(sales_log.postcode_full).to eq(nil)
- expect(sales_log.address_line1).to eq(nil)
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.address_line1_input).to eq(nil)
- expect(sales_log.postcode_full_input).to eq(nil)
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq(nil)
- end
- end
- end
-
- context "and uprn is not confirmed" do
- before do
- choose "No, I want to search for the address instead"
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- sales_log.reload
-
- expect(sales_log.uprn_known).to eq(0) # no
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(nil)
- expect(sales_log.postcode_full).to eq(nil)
- expect(sales_log.address_line1).to eq(nil)
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.address_line1_input).to eq(nil)
- expect(sales_log.postcode_full_input).to eq(nil)
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq(nil)
- end
- end
- end
-
- context "and uprn is not known" do
- before do
- choose "No"
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- sales_log.reload
- expect(sales_log.uprn_known).to eq(0) # no
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(nil)
- expect(sales_log.postcode_full).to eq(nil)
- expect(sales_log.address_line1).to eq(nil)
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.address_line1_input).to eq(nil)
- expect(sales_log.postcode_full_input).to eq(nil)
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq(nil)
- end
-
- context "and the address is not found" do
- it "sets correct address fields" do
- fill_in("sales_log[address_line1_input]", with: "Address line 1")
- fill_in("sales_log[postcode_full_input]", with: "AA1 1AB")
- click_button("Search")
-
- sales_log.reload
- expect(sales_log.uprn_known).to eq(0) # no
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(nil)
- expect(sales_log.postcode_full).to eq(nil)
- expect(sales_log.address_line1).to eq(nil)
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.address_line1_input).to eq("Address line 1")
- expect(sales_log.postcode_full_input).to eq("AA1 1AB")
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq(nil)
-
- click_button("Confirm and continue")
-
- sales_log.reload
- expect(sales_log.uprn_known).to eq(0) # no
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(nil)
- expect(sales_log.postcode_full).to eq(nil)
- expect(sales_log.address_line1).to eq(nil)
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.address_line1_input).to eq("Address line 1")
- expect(sales_log.postcode_full_input).to eq("AA1 1AB")
- expect(sales_log.address_search_value_check).to eq(0)
- expect(sales_log.la).to eq(nil)
- end
- end
-
- context "and address is found, re-searched and not found" do
- before do
- fill_in("sales_log[address_line1_input]", with: "Address line 1")
- fill_in("sales_log[postcode_full_input]", with: "AA1 1AA")
- click_button("Search")
- visit("/sales-logs/#{sales_log.id}/address-matcher")
-
- fill_in("sales_log[address_line1_input]", with: "Address line 1")
- fill_in("sales_log[postcode_full_input]", with: "AA1 1AB")
- click_button("Search")
- end
-
- it "routes to the correct page" do
- expect(page).to have_current_path("/sales-logs/#{sales_log.id}/no-address-found")
- end
- end
-
- context "and the user selects 'address_not_listed'" do
- before do
- fill_in("sales_log[address_line1_input]", with: "Address line 1")
- fill_in("sales_log[postcode_full_input]", with: "AA1 1AA")
- click_button("Search")
- choose "The address is not listed, I want to enter the address manually"
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- sales_log.reload
- expect(sales_log.uprn_known).to eq(0) # no
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq("uprn_not_listed")
- expect(sales_log.pcodenk).to eq(0)
- expect(sales_log.postcode_full).to eq("AA1 1AA")
- expect(sales_log.address_line1).to eq("Address line 1")
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.address_line1_input).to eq("Address line 1")
- expect(sales_log.postcode_full_input).to eq("AA1 1AA")
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq("E09000033")
- end
-
- context "and the user enters a new address manually" do
- context "without changing a valid postcode" do
- before do
- fill_in("sales_log[town_or_city]", with: "Town")
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- sales_log.reload
- expect(sales_log.uprn_known).to eq(0) # no
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq("uprn_not_listed")
- expect(sales_log.pcodenk).to eq(0)
- expect(sales_log.postcode_full).to eq("AA1 1AA")
- expect(sales_log.address_line1).to eq("Address line 1")
- expect(sales_log.address_line2).to eq("")
- expect(sales_log.town_or_city).to eq("Town")
- expect(sales_log.address_line1_input).to eq("Address line 1")
- expect(sales_log.postcode_full_input).to eq("AA1 1AA")
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq("E09000033")
- end
- end
-
- context "with changing the postcode" do
- before do
- fill_in("sales_log[town_or_city]", with: "Town")
- fill_in("sales_log[postcode_full]", with: "AA12AA")
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- sales_log.reload
- expect(sales_log.uprn_known).to eq(0) # no
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq("uprn_not_listed")
- expect(sales_log.pcodenk).to eq(0)
- expect(sales_log.postcode_full).to eq("AA1 2AA")
- expect(sales_log.address_line1).to eq("Address line 1")
- expect(sales_log.address_line2).to eq("")
- expect(sales_log.town_or_city).to eq("Town")
- expect(sales_log.address_line1_input).to eq("Address line 1")
- expect(sales_log.postcode_full_input).to eq("AA1 1AA")
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq("E08000010")
- end
- end
- end
- end
-
- context "and the user selects 'address_not_listed' when partial postcode is given" do
- before do
- fill_in("sales_log[address_line1_input]", with: "Address line 1")
- fill_in("sales_log[postcode_full_input]", with: "1AA")
- click_button("Search")
- choose "The address is not listed, I want to enter the address manually"
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- sales_log.reload
- expect(sales_log.uprn_known).to eq(0) # no
- expect(sales_log.uprn).to eq(nil)
- expect(sales_log.uprn_confirmed).to eq(nil)
- expect(sales_log.uprn_selection).to eq("uprn_not_listed")
- expect(sales_log.pcodenk).to eq(nil)
- expect(sales_log.postcode_full).to eq(nil)
- expect(sales_log.address_line1).to eq("Address line 1")
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq(nil)
- expect(sales_log.address_line1_input).to eq("Address line 1")
- expect(sales_log.postcode_full_input).to eq("1AA")
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq(nil)
- end
- end
-
- context "and the user selects 'address_not_listed' and then changes their mind and selects an address" do
- before do
- fill_in("sales_log[address_line1_input]", with: "Address line 1")
- fill_in("sales_log[postcode_full_input]", with: "AA1 1AA")
- click_button("Search")
- choose "The address is not listed, I want to enter the address manually"
- click_button("Save and continue")
-
- visit("/sales-logs/#{sales_log.id}/uprn-selection")
- choose("sales-log-uprn-selection-111-field", allow_label_click: true)
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- sales_log.reload
- expect(sales_log.uprn_known).to eq(1)
- expect(sales_log.uprn).to eq("111")
- expect(sales_log.uprn_confirmed).to eq(1)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(0)
- expect(sales_log.postcode_full).to eq("AA1 1AA")
- expect(sales_log.address_line1).to eq("Some Place")
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq("Bristol")
- expect(sales_log.address_line1_input).to eq("Address line 1")
- expect(sales_log.postcode_full_input).to eq("AA1 1AA")
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq("E09000033")
- end
- end
-
- context "and possible addresses found and selected" do
- before do
- fill_in("sales_log[address_line1_input]", with: "Address line 1")
- fill_in("sales_log[postcode_full_input]", with: "AA1 1AA")
- click_button("Search")
- choose("sales-log-uprn-selection-111-field", allow_label_click: true)
- click_button("Save and continue")
- end
-
- it "sets correct address fields" do
- sales_log.reload
- expect(sales_log.uprn_known).to eq(1)
- expect(sales_log.uprn).to eq("111")
- expect(sales_log.uprn_confirmed).to eq(1)
- expect(sales_log.uprn_selection).to eq(nil)
- expect(sales_log.pcodenk).to eq(0)
- expect(sales_log.postcode_full).to eq("AA1 1AA")
- expect(sales_log.address_line1).to eq("Some Place")
- expect(sales_log.address_line2).to eq(nil)
- expect(sales_log.town_or_city).to eq("Bristol")
- expect(sales_log.address_line1_input).to eq("Address line 1")
- expect(sales_log.postcode_full_input).to eq("AA1 1AA")
- expect(sales_log.address_search_value_check).to eq(nil)
- expect(sales_log.la).to eq("E09000033")
- end
- end
- end
- end
end
context "when a log becomes a duplicate" do
diff --git a/spec/fixtures/files/sales_logs_csv_export_codes_24.csv b/spec/fixtures/files/sales_logs_csv_export_codes_24.csv
index e0ebccb38..f874e4e75 100644
--- a/spec/fixtures/files/sales_logs_csv_export_codes_24.csv
+++ b/spec/fixtures/files/sales_logs_csv_export_codes_24.csv
@@ -1,3 +1,3 @@
Log ID,Status of log,ID of a set of duplicate logs,Time and date the log was created,Time and date the log was last updated,Year collection period opened,Was the log submitted in-service or via bulk upload?,ID of a set of bulk uploaded logs,Is the user in the created_by column the data protection officer?,Day of sale completion date,Month of sale completion date,Year of sale completion date,Which organisation owned this property before the sale?,Which organisation reported the sale?,User that created the log,User the log is assigned to,What is the purchaser code?,Was this purchase made through an ownership scheme?,What is the type of shared ownership/discounted ownership/outright sale?,"If type = 'Other', what is the type of outright sale?",Is the buyer a company?,Will the buyer(s) live in the property?,Is this a joint purchase?,Are there more than 2 joint buyers of this property?,Did you interview the buyer to answer these questions?,Has the buyer seen the MHCLG privacy notice?,What is the UPRN of the property?,Address line 1,Address line 2,Town/City,County,Postcode,The internal value to indicate if the LA was inferred from the postcode,LA name,LA code,UPRN of the address selected,Was the 'No address found' page seen?,Address line 1 input from address matching feature,Postcode input from address matching feature,Address line 1 entered in bulk upload file,Address line 2 entered in bulk upload file,Town or city entered in bulk upload file,County entered in bulk upload file,Postcode entered in bulk upload file,Local authority entered in bulk upload file,How many bedrooms does the property have?,What type of unit is the property?,Which type of building is the property?,Is the property built or adapted to wheelchair-user standards?,What is buyer 1's age?,Which of these best describes buyer 1's gender identity?,What is buyer 1's ethnic group?,Which of the following best describes buyer 1's ethnic background?,What is buyer 1's nationality?,Which of these best describes buyer 1's working situation?,Will buyer 1 live in the property?,What is buyer 2 or person 2's relationship to buyer 1?,What is buyer 2 or person 2's age?,Which of these best describes buyer 2 or person 2's gender identity?,What is buyer 2's ethnic group?,Which of the following best describes buyer 2's ethnic background?,What is buyer 2's nationality?,What is buyer 2 or person 2's working situation?,Will buyer 2 live in the property?,"Besides the buyer(s), how many other people live or will live in the property?",What is person 3's relationship to buyer 1?,What is person 3's age?,What is person 3's gender identity?,What is person 3's working situation?,What is person 4's relationship to buyer 1?,What is person 4's age?,What is person 4's gender identity?,What is person 4's working situation?,What is person 5's relationship to buyer 1?,What is person 5's age?,What is person 5's gender identity?,What is person 5's working situation?,What is person 6's relationship to buyer 1?,What is person 6's age?,What is person 6's gender identity?,What is person 6's working situation?,What was buyer 1's previous tenure?,Do you know the postcode of buyer 1's last settled accommodation?,Part 1 of postcode of buyer 1's last settled accommodation,Part 2 of postcode of buyer 1's last settled accommodation,Do you know the local authority of buyer 1's last settled accommodation?,The local authority code of buyer 1's last settled accommodation,The local authority name of buyer 1's last settled accommodation,Was the buyer registered with their PRP (HA)?,Was the buyer registered with another PRP (HA)?,Was the buyer registered with the local authority?,Was the buyer registered with a Help to Buy agent?,"Populated if pregyrha, pregother, pregla and pregghb are blank","At the time of purchase, was buyer 2 living at the same address as buyer 1?",What was buyer 2's previous tenure?,Have any of the buyers ever served as a regular in the UK armed forces?,Is the buyer still serving in the UK armed forces?,Are any of the buyers a spouse or civil partner of a UK armed forces regular who died in service within the last 2 years?,Does anyone in the household consider themselves to have a disability?,Does anyone in the household use a wheelchair?,Is buyer 1's annual income known?,What is buyer 1's annual income?,Was buyer 1's income used for a mortgage application?,Is buyer 1's annual income known?,What is buyer 2's annual income?,Was buyer 2's income used for a mortgage application?,Were the buyers receiving any of these housing-related benefits immediately before buying this property?,Is the the total amount the buyers had in savings known?,What is the total amount the buyers had in savings before they paid any deposit for the property?,Have any of the buyers previously owned a property?,Was the previous property under shared ownership?,How long did the buyer(s) live in the property before purchasing it?,Is this a staircasing transaction?,What percentage of the property has been bought in this staircasing transaction?,What percentage of the property do the buyers now own in total?,Was this transaction part of a back-to-back staircasing transaction to facilitate sale of the home on the open market?,Is this a resale?,Day of the exchange of contracts,Month of the exchange of contracts,Year of the exchange of contracts,Day of the practical completion or handover date,Month of the practical completion or handover date,Year of the practical completion or handover date,Was the household rehoused under a local authority nominations agreement?,"Was the buyer a private registered provider, housing association or local authority tenant immediately before this sale?",How many bedrooms did the buyer's previous property have?,What was the previous property type?,What was the rent type of buyer's previous tenure?,What is the full purchase price?,Populated if a soft validation is confirmed.,What was the initial percentage equity stake purchased?,Was a mortgage used to buy this property?,What is the mortgage amount?,What is the name of the mortgage lender?,"If mortgagelender = 'Other', what is the name of the mortgage lender?",What is the length of the mortgage in years?,Does this include any extra borrowing?,How much was the cash deposit paid on the property?,How much cash discount was given through Social Homebuy?,What is the basic monthly rent?,Does the property have any monthly leasehold charges?,What are the total monthly leasehold charges for the property?,Populated if a soft validation is confirmed.,What was the percentage discount?,"What was the amount of any loan, grant, discount or subsidy given?"
ID,STATUS,DUPLICATESET,CREATEDDATE,UPLOADDATE,COLLECTIONYEAR,CREATIONMETHOD,BULKUPLOADID,DATAPROTECT,DAY,MONTH,YEAR,OWNINGORGNAME,MANINGORGNAME,CREATEDBY,USERNAME,PURCHID,OWNERSHIP,TYPE,OTHTYPE,COMPANY,LIVEINBUYER,JOINT,JOINTMORE,NOINT,PRIVACYNOTICE,UPRN,ADDRESS1,ADDRESS2,TOWNCITY,COUNTY,POSTCODE,ISLAINFERRED,LANAME,LA,UPRNSELECTED,ADDRESS_SEARCH_VALUE_CHECK,ADDRESS1INPUT,POSTCODEINPUT,BULKADDRESS1,BULKADDRESS2,BULKTOWNCITY,BULKCOUNTY,BULKPOSTCODE,BULKLA,BEDS,PROPTYPE,BUILTYPE,WCHAIR,AGE1,SEX1,ETHNICGROUP1,ETHNIC,NATIONALITYALL1,ECSTAT1,LIVEINBUYER1,RELAT2,AGE2,SEX2,ETHNICGROUP2,ETHNIC2,NATIONALITYALL2,ECSTAT2,LIVEINBUYER2,HHTYPE,RELAT3,AGE3,SEX3,ECSTAT3,RELAT4,AGE4,SEX4,ECSTAT4,RELAT5,AGE5,SEX5,ECSTAT5,RELAT6,AGE6,SEX6,ECSTAT6,PREVTEN,PPCODENK,PPOSTC1,PPOSTC2,PREVIOUSLAKNOWN,PREVLOC,PREVLOCNAME,PREGYRHA,PREGOTHER,PREGLA,PREGGHB,PREGBLANK,BUY2LIVING,PREVTEN2,HHREGRES,HHREGRESSTILL,ARMEDFORCESSPOUSE,DISABLED,WHEEL,INC1NK,INCOME1,INC1MORT,INC2NK,INCOME2,INC2MORT,HB,SAVINGSNK,SAVINGS,PREVOWN,PREVSHARED,PROPLEN,STAIRCASE,STAIRBOUGHT,STAIROWNED,STAIRCASETOSALE,RESALE,EXDAY,EXMONTH,EXYEAR,HODAY,HOMONTH,HOYEAR,LANOMAGR,SOCTEN,FROMBEDS,FROMPROP,SOCPREVTEN,VALUE,VALUE_VALUE_CHECK,EQUITY,MORTGAGEUSED,MORTGAGE,MORTGAGELENDER,MORTGAGELENDEROTHER,MORTLEN1,EXTRABOR,DEPOSIT,CASHDIS,MRENT,HASMSCHARGE,MSCHARGE,MSCHARGE_VALUE_CHECK,DISCOUNT,GRANT
-,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,1,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,billyboy@eyeklaud.com,,2,8,,,,1,1,2,1,1,"1, Test Street",,Test Town,,AA1 1AA,true,Westminster,E09000033,,,Address line 1,SW1A 1AA,address line 1 as entered,address line 2 as entered,town or city as entered,county as entered,AB1 2CD,la as entered,2,1,1,1,30,X,17,17,826,1,1,P,35,X,17,,826,1,1,3,C,14,X,9,X,-9,X,3,R,-9,R,10,,,,,1,0,SW1A,1AA,1,E09000033,Westminster,1,1,1,1,,3,,1,4,5,1,1,0,13400,1,0,13400,1,4,1,,1,2,10,,,,,,,,,,,,,,,,,110000.0,,,1,20000.0,5,,10,1,80000.0,,,1,100.0,,,10000.0
+,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,1,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,billyboy@eyeklaud.com,,2,8,,,,1,1,2,1,1,"1, Test Street",,Test Town,,AA1 1AA,true,Westminster,E09000033,1,,,,address line 1 as entered,address line 2 as entered,town or city as entered,county as entered,AB1 2CD,la as entered,2,1,1,1,30,X,17,17,826,1,1,P,35,X,17,,826,1,1,3,C,14,X,9,X,-9,X,3,R,-9,R,10,,,,,1,0,SW1A,1AA,1,E09000033,Westminster,1,1,1,1,,3,,1,4,5,1,1,0,13400,1,0,13400,1,4,1,,1,2,10,,,,,,,,,,,,,,,,,110000.0,,,1,20000.0,5,,10,1,80000.0,,,1,100.0,,,10000.0
diff --git a/spec/fixtures/files/sales_logs_csv_export_labels_24.csv b/spec/fixtures/files/sales_logs_csv_export_labels_24.csv
index ffda37642..a66a16201 100644
--- a/spec/fixtures/files/sales_logs_csv_export_labels_24.csv
+++ b/spec/fixtures/files/sales_logs_csv_export_labels_24.csv
@@ -1,3 +1,3 @@
Log ID,Status of log,ID of a set of duplicate logs,Time and date the log was created,Time and date the log was last updated,Year collection period opened,Was the log submitted in-service or via bulk upload?,ID of a set of bulk uploaded logs,Is the user in the created_by column the data protection officer?,Day of sale completion date,Month of sale completion date,Year of sale completion date,Which organisation owned this property before the sale?,Which organisation reported the sale?,User that created the log,User the log is assigned to,What is the purchaser code?,Was this purchase made through an ownership scheme?,What is the type of shared ownership/discounted ownership/outright sale?,"If type = 'Other', what is the type of outright sale?",Is the buyer a company?,Will the buyer(s) live in the property?,Is this a joint purchase?,Are there more than 2 joint buyers of this property?,Did you interview the buyer to answer these questions?,Has the buyer seen the MHCLG privacy notice?,"What is the UPRN of the property?",Address line 1,Address line 2,Town/City,County,Postcode,The internal value to indicate if the LA was inferred from the postcode,LA name,LA code,UPRN of the address selected,Was the 'No address found' page seen?,Address line 1 input from address matching feature,Postcode input from address matching feature,Address line 1 entered in bulk upload file,Address line 2 entered in bulk upload file,Town or city entered in bulk upload file,County entered in bulk upload file,Postcode entered in bulk upload file,Local authority entered in bulk upload file,How many bedrooms does the property have?,What type of unit is the property?,Which type of building is the property?,Is the property built or adapted to wheelchair-user standards?,What is buyer 1's age?,Which of these best describes buyer 1's gender identity?,What is buyer 1's ethnic group?,Which of the following best describes buyer 1's ethnic background?,What is buyer 1's nationality?,Which of these best describes buyer 1's working situation?,Will buyer 1 live in the property?,What is buyer 2 or person 2's relationship to buyer 1?,What is buyer 2 or person 2's age?,Which of these best describes buyer 2 or person 2's gender identity?,What is buyer 2's ethnic group?,Which of the following best describes buyer 2's ethnic background?,What is buyer 2's nationality?,What is buyer 2 or person 2's working situation?,Will buyer 2 live in the property?,"Besides the buyer(s), how many other people live or will live in the property?",What is person 3's relationship to buyer 1?,What is person 3's age?,What is person 3's gender identity?,What is person 3's working situation?,What is person 4's relationship to buyer 1?,What is person 4's age?,What is person 4's gender identity?,What is person 4's working situation?,What is person 5's relationship to buyer 1?,What is person 5's age?,What is person 5's gender identity?,What is person 5's working situation?,What is person 6's relationship to buyer 1?,What is person 6's age?,What is person 6's gender identity?,What is person 6's working situation?,What was buyer 1's previous tenure?,Do you know the postcode of buyer 1's last settled accommodation?,Part 1 of postcode of buyer 1's last settled accommodation,Part 2 of postcode of buyer 1's last settled accommodation,Do you know the local authority of buyer 1's last settled accommodation?,The local authority code of buyer 1's last settled accommodation,The local authority name of buyer 1's last settled accommodation,Was the buyer registered with their PRP (HA)?,Was the buyer registered with another PRP (HA)?,Was the buyer registered with the local authority?,Was the buyer registered with a Help to Buy agent?,"Populated if pregyrha, pregother, pregla and pregghb are blank","At the time of purchase, was buyer 2 living at the same address as buyer 1?",What was buyer 2's previous tenure?,Have any of the buyers ever served as a regular in the UK armed forces?,Is the buyer still serving in the UK armed forces?,Are any of the buyers a spouse or civil partner of a UK armed forces regular who died in service within the last 2 years?,Does anyone in the household consider themselves to have a disability?,Does anyone in the household use a wheelchair?,Is buyer 1's annual income known?,What is buyer 1's annual income?,Was buyer 1's income used for a mortgage application?,Is buyer 1's annual income known?,What is buyer 2's annual income?,Was buyer 2's income used for a mortgage application?,Were the buyers receiving any of these housing-related benefits immediately before buying this property?,Is the the total amount the buyers had in savings known?,What is the total amount the buyers had in savings before they paid any deposit for the property?,Have any of the buyers previously owned a property?,Was the previous property under shared ownership?,How long did the buyer(s) live in the property before purchasing it?,Is this a staircasing transaction?,What percentage of the property has been bought in this staircasing transaction?,What percentage of the property do the buyers now own in total?,Was this transaction part of a back-to-back staircasing transaction to facilitate sale of the home on the open market?,Is this a resale?,Day of the exchange of contracts,Month of the exchange of contracts,Year of the exchange of contracts,Day of the practical completion or handover date,Month of the practical completion or handover date,Year of the practical completion or handover date,Was the household rehoused under a local authority nominations agreement?,"Was the buyer a private registered provider, housing association or local authority tenant immediately before this sale?",How many bedrooms did the buyer's previous property have?,What was the previous property type?,What was the rent type of buyer's previous tenure?,What is the full purchase price?,Populated if a soft validation is confirmed.,What was the initial percentage equity stake purchased?,Was a mortgage used to buy this property?,What is the mortgage amount?,What is the name of the mortgage lender?,"If mortgagelender = 'Other', what is the name of the mortgage lender?",What is the length of the mortgage in years?,Does this include any extra borrowing?,How much was the cash deposit paid on the property?,How much cash discount was given through Social Homebuy?,What is the basic monthly rent?,Does the property have any monthly leasehold charges?,What are the total monthly leasehold charges for the property?,Populated if a soft validation is confirmed.,What was the percentage discount?,"What was the amount of any loan, grant, discount or subsidy given?"
ID,STATUS,DUPLICATESET,CREATEDDATE,UPLOADDATE,COLLECTIONYEAR,CREATIONMETHOD,BULKUPLOADID,DATAPROTECT,DAY,MONTH,YEAR,OWNINGORGNAME,MANINGORGNAME,CREATEDBY,USERNAME,PURCHID,OWNERSHIP,TYPE,OTHTYPE,COMPANY,LIVEINBUYER,JOINT,JOINTMORE,NOINT,PRIVACYNOTICE,UPRN,ADDRESS1,ADDRESS2,TOWNCITY,COUNTY,POSTCODE,ISLAINFERRED,LANAME,LA,UPRNSELECTED,ADDRESS_SEARCH_VALUE_CHECK,ADDRESS1INPUT,POSTCODEINPUT,BULKADDRESS1,BULKADDRESS2,BULKTOWNCITY,BULKCOUNTY,BULKPOSTCODE,BULKLA,BEDS,PROPTYPE,BUILTYPE,WCHAIR,AGE1,SEX1,ETHNICGROUP1,ETHNIC,NATIONALITYALL1,ECSTAT1,LIVEINBUYER1,RELAT2,AGE2,SEX2,ETHNICGROUP2,ETHNIC2,NATIONALITYALL2,ECSTAT2,LIVEINBUYER2,HHTYPE,RELAT3,AGE3,SEX3,ECSTAT3,RELAT4,AGE4,SEX4,ECSTAT4,RELAT5,AGE5,SEX5,ECSTAT5,RELAT6,AGE6,SEX6,ECSTAT6,PREVTEN,PPCODENK,PPOSTC1,PPOSTC2,PREVIOUSLAKNOWN,PREVLOC,PREVLOCNAME,PREGYRHA,PREGOTHER,PREGLA,PREGGHB,PREGBLANK,BUY2LIVING,PREVTEN2,HHREGRES,HHREGRESSTILL,ARMEDFORCESSPOUSE,DISABLED,WHEEL,INC1NK,INCOME1,INC1MORT,INC2NK,INCOME2,INC2MORT,HB,SAVINGSNK,SAVINGS,PREVOWN,PREVSHARED,PROPLEN,STAIRCASE,STAIRBOUGHT,STAIROWNED,STAIRCASETOSALE,RESALE,EXDAY,EXMONTH,EXYEAR,HODAY,HOMONTH,HOYEAR,LANOMAGR,SOCTEN,FROMBEDS,FROMPROP,SOCPREVTEN,VALUE,VALUE_VALUE_CHECK,EQUITY,MORTGAGEUSED,MORTGAGE,MORTGAGELENDER,MORTGAGELENDEROTHER,MORTLEN1,EXTRABOR,DEPOSIT,CASHDIS,MRENT,HASMSCHARGE,MSCHARGE,MSCHARGE_VALUE_CHECK,DISCOUNT,GRANT
-,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,single log,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,billyboy@eyeklaud.com,,Yes - a discounted ownership scheme,Right to Acquire (RTA),,,,Yes,Yes,Yes,1,1,"1, Test Street",,Test Town,,AA1 1AA,Yes,Westminster,E09000033,,,Address line 1,SW1A 1AA,address line 1 as entered,address line 2 as entered,town or city as entered,county as entered,AB1 2CD,la as entered,2,Flat or maisonette,Purpose built,Yes,30,Non-binary,Buyer prefers not to say,17,United Kingdom,Full-time - 30 hours or more,Yes,Partner,35,Non-binary,Buyer prefers not to say,,United Kingdom,Full-time - 30 hours or more,Yes,3,Child,14,Non-binary,Child under 16,Other,Not known,Non-binary,In government training into work,Prefers not to say,Not known,Prefers not to say,Prefers not to say,,,,,Local authority tenant,Yes,AA1,1AA,Yes,E09000033,Westminster,1,1,1,1,,Don't know,,Yes,Yes,No,Yes,Yes,Yes,13400,Yes,Yes,13400,Yes,Don’t know ,No,,Yes,No,10,,,,,,,,,,,,,,,,,110000.0,,,Yes,20000.0,Cambridge Building Society,,10,Yes,80000.0,,,Yes,100.0,,,10000.0
+,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,single log,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,billyboy@eyeklaud.com,,Yes - a discounted ownership scheme,Right to Acquire (RTA),,,,Yes,Yes,Yes,1,1,"1, Test Street",,Test Town,,AA1 1AA,Yes,Westminster,E09000033,1,,,,address line 1 as entered,address line 2 as entered,town or city as entered,county as entered,AB1 2CD,la as entered,2,Flat or maisonette,Purpose built,Yes,30,Non-binary,Buyer prefers not to say,17,United Kingdom,Full-time - 30 hours or more,Yes,Partner,35,Non-binary,Buyer prefers not to say,,United Kingdom,Full-time - 30 hours or more,Yes,3,Child,14,Non-binary,Child under 16,Other,Not known,Non-binary,In government training into work,Prefers not to say,Not known,Prefers not to say,Prefers not to say,,,,,Local authority tenant,Yes,SW1A,1AA,Yes,E09000033,Westminster,1,1,1,1,,Don't know,,Yes,Yes,No,Yes,Yes,Yes,13400,Yes,Yes,13400,Yes,Don’t know ,No,,Yes,No,10,,,,,,,,,,,,,,,,,110000.0,,,Yes,20000.0,Cambridge Building Society,,10,Yes,80000.0,,,Yes,100.0,,,10000.0
diff --git a/spec/fixtures/files/sales_logs_csv_export_non_support_labels_24.csv b/spec/fixtures/files/sales_logs_csv_export_non_support_labels_24.csv
index 0e9a781f5..a6eaed17a 100644
--- a/spec/fixtures/files/sales_logs_csv_export_non_support_labels_24.csv
+++ b/spec/fixtures/files/sales_logs_csv_export_non_support_labels_24.csv
@@ -1,3 +1,3 @@
Log ID,Status of log,ID of a set of duplicate logs,Time and date the log was created,Time and date the log was last updated,Year collection period opened,Was the log submitted in-service or via bulk upload?,,Is the user in the assigned_to column the data protection officer?,Day of sale completion date,Month of sale completion date,Year of sale completion date,Which organisation owned this property before the sale?,Which organisation reported the sale?,User the log is assigned to,What is the purchaser code?,Was this purchase made through an ownership scheme?,What is the type of shared ownership/discounted ownership/outright sale?,"If type = 'Other', what is the type of outright sale?",Is the buyer a company?,Will the buyer(s) live in the property?,Is this a joint purchase?,Are there more than 2 joint buyers of this property?,Did you interview the buyer to answer these questions?,Has the buyer seen the MHCLG privacy notice?,What is the UPRN of the property?,We found an address that might be this property. Is this the property address?,Address line 1 input from address matching feature,Postcode input from address matching feature,UPRN of the address selected,Address line 1,Address line 2,Town/City,County,Part 1 of the property's postcode,Part 2 of the property's postcode,LA code,LA name,How many bedrooms does the property have?,What type of unit is the property?,Which type of building is the property?,Is the property built or adapted to wheelchair-user standards?,What is buyer 1's age?,Which of these best describes buyer 1's gender identity?,What is buyer 1's ethnic group?,Which of the following best describes buyer 1's ethnic background?,What is buyer 1's nationality?,Which of these best describes buyer 1's working situation?,Will buyer 1 live in the property?,What is buyer 2 or person 2's relationship to buyer 1?,What is buyer 2 or person 2's age?,Which of these best describes buyer 2 or person 2's gender identity?,What is buyer 2's ethnic group?,Which of the following best describes buyer 2's ethnic background?,What is buyer 2's nationality?,What is buyer 2 or person 2's working situation?,Will buyer 2 live in the property?,"Besides the buyer(s), how many other people live or will live in the property?",What is person 3's relationship to buyer 1?,What is person 3's age?,What is person 3's gender identity?,What is person 3's working situation?,What is person 4's relationship to buyer 1?,What is person 4's age?,What is person 4's gender identity?,What is person 4's working situation?,What is person 5's relationship to buyer 1?,What is person 5's age?,What is person 5's gender identity?,What is person 5's working situation?,What is person 6's relationship to buyer 1?,What is person 6's age?,What is person 6's gender identity?,What is person 6's working situation?,What was buyer 1's previous tenure?,Do you know the postcode of buyer 1's last settled accommodation?,Part 1 of postcode of buyer 1's last settled accommodation,Part 2 of postcode of buyer 1's last settled accommodation,Do you know the local authority of buyer 1's last settled accommodation?,The local authority code of buyer 1's last settled accommodation,The local authority name of buyer 1's last settled accommodation,Was the buyer registered with their PRP (HA)?,Was the buyer registered with another PRP (HA)?,Was the buyer registered with the local authority?,Was the buyer registered with a Help to Buy agent?,"Populated if pregyrha, pregother, pregla and pregghb are blank","At the time of purchase, was buyer 2 living at the same address as buyer 1?",What was buyer 2's previous tenure?,Have any of the buyers ever served as a regular in the UK armed forces?,Is the buyer still serving in the UK armed forces?,Are any of the buyers a spouse or civil partner of a UK armed forces regular who died in service within the last 2 years?,Does anyone in the household consider themselves to have a disability?,Does anyone in the household use a wheelchair?,Is buyer 1's annual income known?,What is buyer 1's annual income?,Was buyer 1's income used for a mortgage application?,Is buyer 2's annual income known?,What is buyer 2's annual income?,Was buyer 2's income used for a mortgage application?,Were the buyers receiving any of these housing-related benefits immediately before buying this property?,Is the the total amount the buyers had in savings known?,What is the total amount the buyers had in savings before they paid any deposit for the property?,Have any of the buyers previously owned a property?,Was the previous property under shared ownership?,How long did the buyer(s) live in the property before purchasing it?,Is this a staircasing transaction?,What percentage of the property has been bought in this staircasing transaction?,What percentage of the property do the buyers now own in total?,Was this transaction part of a back-to-back staircasing transaction to facilitate sale of the home on the open market?,Is this a resale?,Day of the exchange of contracts,Month of the exchange of contracts,Year of the exchange of contracts,Day of the practical completion or handover date,Month of the practical completion or handover date,Year of the practical completion or handover date,Was the household rehoused under a local authority nominations agreement?,"Was the buyer a private registered provider, housing association or local authority tenant immediately before this sale?",How many bedrooms did the buyer's previous property have?,What was the previous property type?,What was the rent type of buyer's previous tenure?,What is the full purchase price?,What was the initial percentage equity stake purchased?,Was a mortgage used to buy this property?,What is the mortgage amount?,What is the name of the mortgage lender?,"If mortgagelender = 'Other', what is the name of the mortgage lender?",What is the length of the mortgage in years?,Does this include any extra borrowing?,How much was the cash deposit paid on the property?,How much cash discount was given through Social Homebuy?,What is the basic monthly rent?,Does the property have any monthly leasehold charges?,What are the total monthly leasehold charges for the property?,What was the percentage discount?,"What was the amount of any loan, grant, discount or subsidy given?"
id,status,duplicate_set_id,created_at,updated_at,collection_start_year,creation_method,bulk_upload_id,is_dpo,day,month,year,owning_organisation_name,managing_organisation_name,assigned_to,purchid,ownershipsch,type,othtype,companybuy,buylivein,jointpur,jointmore,noint,privacynotice,uprn,uprn_confirmed,address_line1_input,postcode_full_input,uprn_selection,address_line1,address_line2,town_or_city,county,pcode1,pcode2,la,la_label,beds,proptype,builtype,wchair,age1,sex1,ethnic_group,ethnic,nationality_all,ecstat1,buy1livein,relat2,age2,sex2,ethnic_group2,ethnicbuy2,nationality_all_buyer2,ecstat2,buy2livein,hholdcount,relat3,age3,sex3,ecstat3,relat4,age4,sex4,ecstat4,relat5,age5,sex5,ecstat5,relat6,age6,sex6,ecstat6,prevten,ppcodenk,ppostc1,ppostc2,previous_la_known,prevloc,prevloc_label,pregyrha,pregother,pregla,pregghb,pregblank,buy2living,prevtenbuy2,hhregres,hhregresstill,armedforcesspouse,disabled,wheel,income1nk,income1,inc1mort,income2nk,income2,inc2mort,hb,savingsnk,savings,prevown,prevshared,proplen,staircase,stairbought,stairowned,staircasesale,resale,exday,exmonth,exyear,hoday,homonth,hoyear,lanomagr,soctenant,frombeds,fromprop,socprevten,value,equity,mortgageused,mortgage,mortgagelender,mortgagelenderother,mortlen,extrabor,deposit,cashdis,mrent,has_mscharge,mscharge,discount,grant
-,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,single log,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,,Yes - a discounted ownership scheme,Right to Acquire (RTA),,,,Yes,Yes,Yes,1,1,Yes,Address line 1,SW1A 1AA,,"1, Test Street",,Test Town,,AA1,1AA,E09000033,Westminster,2,Flat or maisonette,Purpose built,Yes,30,Non-binary,Buyer prefers not to say,17,United Kingdom,Full-time - 30 hours or more,Yes,Partner,35,Non-binary,Buyer prefers not to say,,United Kingdom,Full-time - 30 hours or more,Yes,3,Child,14,Non-binary,Child under 16,Other,Not known,Non-binary,In government training into work,Prefers not to say,Not known,Prefers not to say,Prefers not to say,,,,,Local authority tenant,Yes,AA1,1AA,Yes,E09000033,Westminster,1,1,1,1,,Don't know,,Yes,Yes,No,Yes,Yes,Yes,13400,Yes,Yes,13400,Yes,Don’t know ,No,,Yes,No,10,,,,,,,,,,,,,,,,,110000.0,,Yes,20000.0,Cambridge Building Society,,10,Yes,80000.0,,,Yes,100.0,,10000.0
+,completed,,2024-05-01T00:00:00+01:00,2024-05-01T00:00:00+01:00,2024,single log,,false,1,5,2024,MHCLG,MHCLG,billyboy@eyeklaud.com,,Yes - a discounted ownership scheme,Right to Acquire (RTA),,,,Yes,Yes,Yes,1,1,Yes,,,1,"1, Test Street",,Test Town,,SW1A,1AA,E09000033,Westminster,2,Flat or maisonette,Purpose built,Yes,30,Non-binary,Buyer prefers not to say,17,United Kingdom,Full-time - 30 hours or more,Yes,Partner,35,Non-binary,Buyer prefers not to say,,United Kingdom,Full-time - 30 hours or more,Yes,3,Child,14,Non-binary,Child under 16,Other,Not known,Non-binary,In government training into work,Prefers not to say,Not known,Prefers not to say,Prefers not to say,,,,,Local authority tenant,Yes,SW1A,1AA,Yes,E09000033,Westminster,1,1,1,1,,Don't know,,Yes,Yes,No,Yes,Yes,Yes,13400,Yes,Yes,13400,Yes,Don’t know ,No,,Yes,No,10,,,,,,,,,,,,,,,,,110000.0,,Yes,20000.0,Cambridge Building Society,,10,Yes,80000.0,,,Yes,100.0,,10000.0
diff --git a/spec/models/bulk_upload_spec.rb b/spec/models/bulk_upload_spec.rb
index 61e16920e..5195d23f4 100644
--- a/spec/models/bulk_upload_spec.rb
+++ b/spec/models/bulk_upload_spec.rb
@@ -24,7 +24,7 @@ RSpec.describe BulkUpload, type: :model do
let(:log) { build(:lettings_log, startdate: Time.zone.local(2025, 4, 2), bulk_upload:) }
it "has the correct number of value checks to be set as confirmed" do
- expect(bulk_upload.fields_to_confirm(log)).to match_array %w[rent_value_check void_date_value_check major_repairs_date_value_check pregnancy_value_check retirement_value_check referral_value_check net_income_value_check scharge_value_check pscharge_value_check supcharg_value_check address_search_value_check multiple_partners_value_check partner_under_16_value_check reasonother_value_check]
+ expect(bulk_upload.fields_to_confirm(log)).to match_array %w[rent_value_check void_date_value_check major_repairs_date_value_check pregnancy_value_check retirement_value_check referral_value_check net_income_value_check scharge_value_check pscharge_value_check supcharg_value_check multiple_partners_value_check partner_under_16_value_check reasonother_value_check]
end
end
@@ -32,7 +32,7 @@ RSpec.describe BulkUpload, type: :model do
let(:log) { build(:sales_log, :saledate_today, bulk_upload:) }
it "has the correct number of value checks to be set as confirmed" do
- expect(bulk_upload.fields_to_confirm(log)).to match_array %w[value_value_check monthly_charges_value_check percentage_discount_value_check income1_value_check income2_value_check combined_income_value_check retirement_value_check old_persons_shared_ownership_value_check buyer_livein_value_check student_not_child_value_check wheel_value_check mortgage_value_check savings_value_check deposit_value_check staircase_bought_value_check stairowned_value_check hodate_check shared_ownership_deposit_value_check extrabor_value_check grant_value_check discounted_sale_value_check deposit_and_mortgage_value_check address_search_value_check multiple_partners_value_check partner_under_16_value_check]
+ expect(bulk_upload.fields_to_confirm(log)).to match_array %w[value_value_check monthly_charges_value_check percentage_discount_value_check income1_value_check income2_value_check combined_income_value_check retirement_value_check old_persons_shared_ownership_value_check buyer_livein_value_check student_not_child_value_check wheel_value_check mortgage_value_check savings_value_check deposit_value_check staircase_bought_value_check stairowned_value_check hodate_check shared_ownership_deposit_value_check extrabor_value_check grant_value_check discounted_sale_value_check deposit_and_mortgage_value_check multiple_partners_value_check partner_under_16_value_check]
end
end
end
diff --git a/spec/models/form/lettings/pages/address_fallback_spec.rb b/spec/models/form/lettings/pages/address_fallback_spec.rb
index d3971d540..ffac6238e 100644
--- a/spec/models/form/lettings/pages/address_fallback_spec.rb
+++ b/spec/models/form/lettings/pages/address_fallback_spec.rb
@@ -24,13 +24,6 @@ RSpec.describe Form::Lettings::Pages::AddressFallback, type: :model do
end
it "has correct depends_on" do
- expect(page.depends_on).to eq([
- { "is_supported_housing?" => false, "uprn_known" => nil, "uprn_selection" => "uprn_not_listed" },
- { "is_supported_housing?" => false, "uprn_known" => 0, "uprn_selection" => "uprn_not_listed" },
- { "is_supported_housing?" => false, "uprn_confirmed" => 0, "uprn_selection" => "uprn_not_listed" },
- { "is_supported_housing?" => false, "uprn_known" => nil, "address_options_present?" => false },
- { "is_supported_housing?" => false, "uprn_known" => 0, "address_options_present?" => false },
- { "is_supported_housing?" => false, "uprn_confirmed" => 0, "address_options_present?" => false },
- ])
+ expect(page.depends_on).to eq([{ "manual_address_entry_selected" => true, "is_supported_housing?" => false }])
end
end
diff --git a/spec/models/form/lettings/pages/address_search_spec.rb b/spec/models/form/lettings/pages/address_search_spec.rb
new file mode 100644
index 000000000..86c6537a1
--- /dev/null
+++ b/spec/models/form/lettings/pages/address_search_spec.rb
@@ -0,0 +1,42 @@
+require "rails_helper"
+
+RSpec.describe Form::Lettings::Pages::AddressSearch, type: :model do
+ subject(:page) { described_class.new(page_id, page_definition, subsection) }
+
+ let(:page_id) { nil }
+ let(:page_definition) { nil }
+ let(:subsection) { instance_double(Form::Subsection, form: instance_double(Form, start_date:)) }
+ let(:start_date) { Time.utc(2024, 4, 1) }
+
+ it "has correct subsection" do
+ expect(page.subsection).to eq(subsection)
+ end
+
+ it "has correct questions" do
+ expect(page.questions.map(&:id)).to eq(%w[uprn])
+ end
+
+ it "has the correct id" do
+ expect(page.id).to eq("address_search")
+ end
+
+ it "has the correct description" do
+ expect(page.description).to be_nil
+ end
+
+ it "has correct depends_on" do
+ expect(page.depends_on).to eq([{ "is_supported_housing?" => false, "manual_address_entry_selected" => false }])
+ end
+
+ it "has the correct question number" do
+ expect(page.question_number).to eq(12)
+ end
+
+ context "with 2025/26 form" do
+ let(:start_date) { Time.utc(2025, 4, 1) }
+
+ it "has the correct question number" do
+ expect(page.question_number).to eq(16)
+ end
+ end
+end
diff --git a/spec/models/form/lettings/questions/address_search_spec.rb b/spec/models/form/lettings/questions/address_search_spec.rb
new file mode 100644
index 000000000..d063a94dc
--- /dev/null
+++ b/spec/models/form/lettings/questions/address_search_spec.rb
@@ -0,0 +1,68 @@
+require "rails_helper"
+
+RSpec.describe Form::Lettings::Questions::AddressSearch, type: :model do
+ subject(:question) { described_class.new(question_id, question_definition, page) }
+
+ let(:question_id) { nil }
+ let(:question_definition) { nil }
+ let(:page) { instance_double(Form::Page, subsection: instance_double(Form::Subsection, form: instance_double(Form, start_date:))) }
+ let(:start_date) { Time.utc(2024, 4, 1) }
+
+ it "has correct page" do
+ expect(question.page).to eq(page)
+ end
+
+ it "has the correct id" do
+ expect(question.id).to eq("uprn")
+ end
+
+ it "has the correct type" do
+ expect(question.type).to eq("address_search")
+ end
+
+ it "has the correct question number" do
+ expect(question.question_number).to eq(12)
+ end
+
+ context "with 2025/26 form" do
+ let(:start_date) { Time.utc(2025, 4, 1) }
+
+ it "has the correct question number" do
+ expect(question.question_number).to eq(16)
+ end
+ end
+
+ describe "get_extra_check_answer_value" do
+ context "when address is not present" do
+ let(:log) { build(:lettings_log, manual_address_entry_selected: false) }
+
+ it "returns nil" do
+ expect(question.get_extra_check_answer_value(log)).to be_nil
+ end
+ end
+
+ context "when address search is present" do
+ let(:log) do
+ build(
+ :lettings_log,
+ :completed,
+ address_line1: "19, Charlton Gardens",
+ town_or_city: "Bristol",
+ postcode_full: "BS10 6LU",
+ la: "E06000023",
+ uprn_known: 1,
+ uprn: 107,
+ uprn_confirmed: 1,
+ )
+ end
+
+ context "when uprn known" do
+ it "returns formatted value" do
+ expect(question.get_extra_check_answer_value(log)).to eq(
+ "\n\n19, Charlton Gardens\nBristol\nBS10 6LU\nBristol, City of",
+ )
+ end
+ end
+ end
+ end
+end
diff --git a/spec/models/form/lettings/questions/uprn_selection_spec.rb b/spec/models/form/lettings/questions/uprn_selection_spec.rb
index c3edc646e..e10b22d89 100644
--- a/spec/models/form/lettings/questions/uprn_selection_spec.rb
+++ b/spec/models/form/lettings/questions/uprn_selection_spec.rb
@@ -90,9 +90,10 @@ RSpec.describe Form::Lettings::Questions::UprnSelection, type: :model do
context "when the log has address line 1 input only" do
before do
+ allow(address_client_instance).to receive(:result).and_return(nil)
log.address_line1_input = "Address line 1"
log.postcode_full_input = nil
- log.save!(valudate: false)
+ log.save!(validate: false)
end
it "has the correct input_playback" do
@@ -102,9 +103,10 @@ RSpec.describe Form::Lettings::Questions::UprnSelection, type: :model do
context "when the log has postcode input only" do
before do
+ allow(address_client_instance).to receive(:result).and_return(nil)
log.address_line1_input = nil
log.postcode_full_input = "A1 1AA"
- log.save!(valudate: false)
+ log.save!(validate: false)
end
it "has the correct input_playback" do
@@ -116,7 +118,7 @@ RSpec.describe Form::Lettings::Questions::UprnSelection, type: :model do
before do
log.address_line1_input = "Address line 1"
log.postcode_full_input = "A1 1AA"
- log.save!(valudate: false)
+ log.save!(validate: false)
end
it "has the correct input_playback" do
diff --git a/spec/models/form/lettings/questions/uprn_spec.rb b/spec/models/form/lettings/questions/uprn_spec.rb
index 8bb932b35..0c3ecec85 100644
--- a/spec/models/form/lettings/questions/uprn_spec.rb
+++ b/spec/models/form/lettings/questions/uprn_spec.rb
@@ -52,12 +52,14 @@ RSpec.describe Form::Lettings::Questions::Uprn, type: :model do
la: "E09000003",
uprn_known:,
uprn:,
+ manual_address_entry_selected:,
)
end
context "when uprn known nil" do
let(:uprn_known) { nil }
let(:uprn) { nil }
+ let(:manual_address_entry_selected) { true }
it "returns formatted value" do
expect(question.get_extra_check_answer_value(log)).to be_nil
@@ -67,6 +69,7 @@ RSpec.describe Form::Lettings::Questions::Uprn, type: :model do
context "when uprn known" do
let(:uprn_known) { 1 }
let(:uprn) { 1 }
+ let(:manual_address_entry_selected) { false }
it "returns formatted value" do
expect(question.get_extra_check_answer_value(log)).to eq(
@@ -78,6 +81,7 @@ RSpec.describe Form::Lettings::Questions::Uprn, type: :model do
context "when uprn not known" do
let(:uprn_known) { 0 }
let(:uprn) { nil }
+ let(:manual_address_entry_selected) { true }
it "returns formatted value" do
expect(question.get_extra_check_answer_value(log)).to be_nil
diff --git a/spec/models/form/lettings/subsections/property_information_spec.rb b/spec/models/form/lettings/subsections/property_information_spec.rb
index e0e9a61ae..2630c83d4 100644
--- a/spec/models/form/lettings/subsections/property_information_spec.rb
+++ b/spec/models/form/lettings/subsections/property_information_spec.rb
@@ -64,11 +64,7 @@ RSpec.describe Form::Lettings::Subsections::PropertyInformation, type: :model do
it "has correct pages" do
expect(property_information.pages.map(&:id)).to eq(
%w[
- uprn
- uprn_confirmation
- address_matcher
- no_address_found
- uprn_selection
+ address_search
address
property_local_authority
local_authority_rent_value_check
@@ -105,11 +101,7 @@ RSpec.describe Form::Lettings::Subsections::PropertyInformation, type: :model do
property_let_type
property_vacancy_reason_not_first_let
property_vacancy_reason_first_let
- uprn
- uprn_confirmation
- address_matcher
- no_address_found
- uprn_selection
+ address_search
address
property_local_authority
local_authority_rent_value_check
diff --git a/spec/models/form/sales/pages/address_fallback_spec.rb b/spec/models/form/sales/pages/address_fallback_spec.rb
index 4c48a46fe..35bb6cd24 100644
--- a/spec/models/form/sales/pages/address_fallback_spec.rb
+++ b/spec/models/form/sales/pages/address_fallback_spec.rb
@@ -24,13 +24,6 @@ RSpec.describe Form::Sales::Pages::AddressFallback, type: :model do
end
it "has correct depends_on" do
- expect(page.depends_on).to eq([
- { "uprn_known" => nil, "uprn_selection" => "uprn_not_listed" },
- { "uprn_known" => 0, "uprn_selection" => "uprn_not_listed" },
- { "uprn_confirmed" => 0, "uprn_selection" => "uprn_not_listed" },
- { "uprn_known" => nil, "address_options_present?" => false },
- { "uprn_known" => 0, "address_options_present?" => false },
- { "uprn_confirmed" => 0, "address_options_present?" => false },
- ])
+ expect(page.depends_on).to eq([{ "manual_address_entry_selected" => true }])
end
end
diff --git a/spec/models/form/sales/pages/address_search_spec.rb b/spec/models/form/sales/pages/address_search_spec.rb
new file mode 100644
index 000000000..670854694
--- /dev/null
+++ b/spec/models/form/sales/pages/address_search_spec.rb
@@ -0,0 +1,42 @@
+require "rails_helper"
+
+RSpec.describe Form::Sales::Pages::AddressSearch, type: :model do
+ subject(:page) { described_class.new(page_id, page_definition, subsection) }
+
+ let(:page_id) { nil }
+ let(:page_definition) { nil }
+ let(:subsection) { instance_double(Form::Subsection, form: instance_double(Form, start_date:)) }
+ let(:start_date) { Time.utc(2024, 4, 1) }
+
+ it "has correct subsection" do
+ expect(page.subsection).to eq(subsection)
+ end
+
+ it "has correct questions" do
+ expect(page.questions.map(&:id)).to eq(%w[uprn])
+ end
+
+ it "has the correct id" do
+ expect(page.id).to eq("address_search")
+ end
+
+ it "has the correct description" do
+ expect(page.description).to be_nil
+ end
+
+ it "has correct depends_on" do
+ expect(page.depends_on).to eq([{ "manual_address_entry_selected" => false }])
+ end
+
+ it "has the correct question number" do
+ expect(page.question_number).to eq(15)
+ end
+
+ context "with 2025/26 form" do
+ let(:start_date) { Time.utc(2025, 4, 1) }
+
+ it "has the correct question number" do
+ expect(page.question_number).to eq(13)
+ end
+ end
+end
diff --git a/spec/models/form/sales/pages/uprn_confirmation_spec.rb b/spec/models/form/sales/pages/uprn_confirmation_spec.rb
index 9550b9f49..6415c2eb0 100644
--- a/spec/models/form/sales/pages/uprn_confirmation_spec.rb
+++ b/spec/models/form/sales/pages/uprn_confirmation_spec.rb
@@ -7,6 +7,10 @@ RSpec.describe Form::Sales::Pages::UprnConfirmation, type: :model do
let(:page_definition) { nil }
let(:subsection) { instance_double(Form::Subsection) }
+ before do
+ allow(subsection).to receive(:form).and_return(instance_double(Form, start_year_2024_or_later?: false))
+ end
+
it "has correct subsection" do
expect(page.subsection).to eq(subsection)
end
diff --git a/spec/models/form/sales/questions/address_search_spec.rb b/spec/models/form/sales/questions/address_search_spec.rb
new file mode 100644
index 000000000..bb30cbfa0
--- /dev/null
+++ b/spec/models/form/sales/questions/address_search_spec.rb
@@ -0,0 +1,68 @@
+require "rails_helper"
+
+RSpec.describe Form::Sales::Questions::AddressSearch, type: :model do
+ subject(:question) { described_class.new(question_id, question_definition, page) }
+
+ let(:question_id) { nil }
+ let(:question_definition) { nil }
+ let(:page) { instance_double(Form::Page, subsection: instance_double(Form::Subsection, form: instance_double(Form, start_date:))) }
+ let(:start_date) { Time.utc(2024, 4, 1) }
+
+ it "has correct page" do
+ expect(question.page).to eq(page)
+ end
+
+ it "has the correct id" do
+ expect(question.id).to eq("uprn")
+ end
+
+ it "has the correct type" do
+ expect(question.type).to eq("address_search")
+ end
+
+ it "has the correct question number" do
+ expect(question.question_number).to eq(15)
+ end
+
+ context "with 2025/26 form" do
+ let(:start_date) { Time.utc(2025, 4, 1) }
+
+ it "has the correct question number" do
+ expect(question.question_number).to eq(13)
+ end
+ end
+
+ describe "get_extra_check_answer_value" do
+ context "when address is not present" do
+ let(:log) { build(:sales_log, manual_address_entry_selected: false) }
+
+ it "returns nil" do
+ expect(question.get_extra_check_answer_value(log)).to be_nil
+ end
+ end
+
+ context "when address search is present" do
+ let(:log) do
+ build(
+ :sales_log,
+ :completed,
+ address_line1: "19, Charlton Gardens",
+ town_or_city: "Bristol",
+ postcode_full: "BS10 6LU",
+ la: "E06000023",
+ uprn_known: 1,
+ uprn: 107,
+ uprn_confirmed: 1,
+ )
+ end
+
+ context "when uprn known" do
+ it "returns formatted value" do
+ expect(question.get_extra_check_answer_value(log)).to eq(
+ "\n\n19, Charlton Gardens\nBristol\nBS10 6LU\nBristol, City of",
+ )
+ end
+ end
+ end
+ end
+end
diff --git a/spec/models/form/sales/questions/uprn_selection_spec.rb b/spec/models/form/sales/questions/uprn_selection_spec.rb
index ff1b1a6dd..efcf39c67 100644
--- a/spec/models/form/sales/questions/uprn_selection_spec.rb
+++ b/spec/models/form/sales/questions/uprn_selection_spec.rb
@@ -90,9 +90,10 @@ RSpec.describe Form::Sales::Questions::UprnSelection, type: :model do
context "when the log has address line 1 input only" do
before do
+ allow(address_client_instance).to receive(:result).and_return(nil)
log.address_line1_input = "Address line 1"
log.postcode_full_input = nil
- log.save!(valudate: false)
+ log.save!(validate: false)
end
it "has the correct input_playback" do
@@ -102,9 +103,10 @@ RSpec.describe Form::Sales::Questions::UprnSelection, type: :model do
context "when the log has postcode input only" do
before do
+ allow(address_client_instance).to receive(:result).and_return(nil)
log.address_line1_input = nil
log.postcode_full_input = "A1 1AA"
- log.save!(valudate: false)
+ log.save!(validate: false)
end
it "has the correct input_playback" do
@@ -116,7 +118,7 @@ RSpec.describe Form::Sales::Questions::UprnSelection, type: :model do
before do
log.address_line1_input = "Address line 1"
log.postcode_full_input = "A1 1AA"
- log.save!(valudate: false)
+ log.save!(validate: false)
end
it "has the correct input_playback" do
diff --git a/spec/models/form/sales/subsections/property_information_spec.rb b/spec/models/form/sales/subsections/property_information_spec.rb
index ccfeb8e3a..7585d290a 100644
--- a/spec/models/form/sales/subsections/property_information_spec.rb
+++ b/spec/models/form/sales/subsections/property_information_spec.rb
@@ -55,11 +55,7 @@ RSpec.describe Form::Sales::Subsections::PropertyInformation, type: :model do
it "has correct pages" do
expect(property_information.pages.map(&:id)).to eq(
%w[
- uprn
- uprn_confirmation
- address_matcher
- no_address_found
- uprn_selection
+ address_search
address
property_local_authority
local_authority_buyer_1_income_max_value_check
@@ -89,11 +85,7 @@ RSpec.describe Form::Sales::Subsections::PropertyInformation, type: :model do
it "has correct pages" do
expect(property_information.pages.map(&:id)).to eq(
%w[
- uprn
- uprn_confirmation
- address_matcher
- no_address_found
- uprn_selection
+ address_search
address
property_local_authority
local_authority_buyer_1_income_max_value_check
diff --git a/spec/models/sales_log_spec.rb b/spec/models/sales_log_spec.rb
index c36884b8d..442febddb 100644
--- a/spec/models/sales_log_spec.rb
+++ b/spec/models/sales_log_spec.rb
@@ -566,6 +566,7 @@ RSpec.describe SalesLog, type: :model do
ppostcode_full: nil,
prevloc: nil,
saledate: Time.zone.local(2024, 5, 2),
+ manual_address_entry_selected: true,
})
end
@@ -617,7 +618,7 @@ RSpec.describe SalesLog, type: :model do
end
let(:address_sales_log_25_26) do
- create(:sales_log, :shared_ownership_setup_complete, postcode_full: "CA10 1AA", saledate: Time.zone.local(2025, 5, 2))
+ create(:sales_log, :shared_ownership_setup_complete, postcode_full: "CA10 1AA", saledate: Time.zone.local(2025, 5, 2), manual_address_entry_selected: true)
end
before do
@@ -672,11 +673,11 @@ RSpec.describe SalesLog, type: :model do
context "when saving address with LAs that have changed E-codes" do
context "when address inferred from uprn - we still get LA from postcode" do
let(:address_sales_log_24_25) do
- create(:sales_log, :shared_ownership_setup_complete, uprn_known: 1, uprn: 1, saledate: Time.zone.local(2024, 5, 2))
+ create(:sales_log, :shared_ownership_setup_complete, manual_address_entry_selected: false, uprn_known: 1, uprn: 1, saledate: Time.zone.local(2024, 5, 2))
end
let(:address_sales_log_25_26) do
- create(:sales_log, :shared_ownership_setup_complete, uprn_known: 1, uprn: 1, saledate: Time.zone.local(2025, 5, 2))
+ create(:sales_log, :shared_ownership_setup_complete, manual_address_entry_selected: false, uprn_known: 1, uprn: 1, saledate: Time.zone.local(2025, 5, 2))
end
before do
diff --git a/spec/models/validations/sales/property_validations_spec.rb b/spec/models/validations/sales/property_validations_spec.rb
index c5af3ae78..62b65ee36 100644
--- a/spec/models/validations/sales/property_validations_spec.rb
+++ b/spec/models/validations/sales/property_validations_spec.rb
@@ -136,9 +136,9 @@ RSpec.describe Validations::Sales::PropertyValidations do
context "when within the limit and only numeric" do
let(:record) { build(:sales_log, uprn: "123456789012") }
- it "does not add an error" do
+ it "does not add an invalid UPRN error" do
property_validator.validate_uprn(record)
- expect(record.errors).not_to be_present
+ expect(record.errors.added?(:uprn, I18n.t("validations.sales.property_information.uprn.invalid"))).to be false
end
end
end
diff --git a/spec/request_helper.rb b/spec/request_helper.rb
index f1f208ec6..2e0cc3d70 100644
--- a/spec/request_helper.rb
+++ b/spec/request_helper.rb
@@ -20,7 +20,7 @@ module RequestHelper
body = { results: [{ DPA: { UPRN: "10033558653" } }] }.to_json
WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/find?key&maxresults=10&minmatch=0.4&query=Address%20line%201,%20SW1A%201AA")
.to_return(status: 200, body:, headers: {})
- body = { results: [{ DPA: { "POSTCODE": "SW1A 1AA", "POST_TOWN": "London" } }] }.to_json
+ body = { results: [{ DPA: { "POSTCODE": "SW1A 1AA", "POST_TOWN": "London", "PO_BOX_NUMBER": "The Mall, City Of Westminster" } }] }.to_json
WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/uprn?dataset=DPA,LPI&key&uprn=1")
.to_return(status: 200, body:, headers: {})
WebMock.stub_request(:get, "https://api.os.uk/search/places/v1/uprn?dataset=DPA,LPI&key&uprn=10033558653")
diff --git a/spec/requests/address_search_controller_spec.rb b/spec/requests/address_search_controller_spec.rb
new file mode 100644
index 000000000..5c2acd11a
--- /dev/null
+++ b/spec/requests/address_search_controller_spec.rb
@@ -0,0 +1,148 @@
+require "rails_helper"
+
+RSpec.describe AddressSearchController, type: :request do
+ let(:user) { create(:user) }
+
+ before do
+ sign_in user
+ end
+
+ describe "#manual input" do
+ context "when no address data is given and user chooses to enter address manually" do
+ let(:sales_log) { create(:sales_log, :shared_ownership_setup_complete, manual_address_entry_selected: false, assigned_to: user) }
+
+ it "correctly sets address fields" do
+ sales_log.reload
+ expect(sales_log.manual_address_entry_selected).to eq(false)
+ expect(sales_log.uprn_known).to eq(nil)
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(nil)
+ expect(sales_log.postcode_full).to eq(nil)
+ expect(sales_log.address_line1).to eq(nil)
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.la).to eq(nil)
+
+ get "/address-search/manual-input/sales_log/#{sales_log.id}"
+
+ sales_log.reload
+ expect(sales_log.manual_address_entry_selected).to eq(true)
+ expect(sales_log.uprn_known).to eq(0)
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(nil)
+ expect(sales_log.postcode_full).to eq(nil)
+ expect(sales_log.address_line1).to eq(nil)
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.la).to eq(nil)
+ end
+ end
+
+ context "when choosing to manually input an address for a log that has an address searched value" do
+ let(:lettings_log) { create(:lettings_log, :completed, manual_address_entry_selected: false, assigned_to: user) }
+
+ it "correctly sets address fields" do
+ lettings_log.reload
+ expect(lettings_log.uprn_known).to eq(1)
+ expect(lettings_log.uprn).to eq("10033558653")
+ expect(lettings_log.uprn_confirmed).to eq(1)
+ expect(lettings_log.uprn_selection).to eq("10033558653")
+ expect(lettings_log.postcode_known).to eq(1)
+ expect(lettings_log.postcode_full).to eq("SW1A 1AA")
+ expect(lettings_log.address_line1).to eq("The Mall, City Of Westminster")
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq("London")
+ expect(lettings_log.la).to eq("E09000033")
+
+ get "/address-search/manual-input/lettings_log/#{lettings_log.id}"
+
+ lettings_log.reload
+ expect(lettings_log.manual_address_entry_selected).to eq(true)
+ expect(lettings_log.uprn_known).to eq(0)
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(nil)
+ expect(lettings_log.postcode_full).to eq(nil)
+ expect(lettings_log.address_line1).to eq(nil)
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.la).to eq(nil)
+ end
+ end
+ end
+
+ describe "#search input" do
+ context "when no address is entered manually and choosing to search instead" do
+ let(:lettings_log) { create(:lettings_log, :setup_completed, manual_address_entry_selected: true, assigned_to: user) }
+
+ it "correctly sets address fields" do
+ lettings_log.reload
+ expect(lettings_log.manual_address_entry_selected).to eq(true)
+ expect(lettings_log.uprn_known).to eq(0)
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(nil)
+ expect(lettings_log.postcode_full).to eq(nil)
+ expect(lettings_log.address_line1).to eq(nil)
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.la).to eq(nil)
+
+ get "/address-search/search-input/lettings_log/#{lettings_log.id}"
+
+ lettings_log.reload
+ expect(lettings_log.manual_address_entry_selected).to eq(false)
+ expect(lettings_log.uprn_known).to eq(nil)
+ expect(lettings_log.uprn).to eq(nil)
+ expect(lettings_log.uprn_confirmed).to eq(nil)
+ expect(lettings_log.uprn_selection).to eq(nil)
+ expect(lettings_log.postcode_known).to eq(nil)
+ expect(lettings_log.postcode_full).to eq(nil)
+ expect(lettings_log.address_line1).to eq(nil)
+ expect(lettings_log.address_line2).to eq(nil)
+ expect(lettings_log.town_or_city).to eq(nil)
+ expect(lettings_log.la).to eq(nil)
+ end
+ end
+
+ context "when choosing to search for an address for a log that has an address searched value" do
+ let(:sales_log) { create(:sales_log, :completed, manual_address_entry_selected: true, town_or_city: "Test Town", assigned_to: user) }
+
+ it "correctly sets address fields" do
+ sales_log.reload
+ expect(sales_log.manual_address_entry_selected).to eq(true)
+ expect(sales_log.uprn_known).to eq(0)
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(0)
+ expect(sales_log.postcode_full).to eq("SW1A 1AA")
+ expect(sales_log.address_line1).to eq("Address line 1")
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq("Test Town")
+ expect(sales_log.la).to eq("E09000033")
+
+ get "/address-search/search-input/sales_log/#{sales_log.id}"
+
+ sales_log.reload
+ expect(sales_log.manual_address_entry_selected).to eq(false)
+ expect(sales_log.uprn_known).to eq(nil)
+ expect(sales_log.uprn).to eq(nil)
+ expect(sales_log.uprn_confirmed).to eq(nil)
+ expect(sales_log.uprn_selection).to eq(nil)
+ expect(sales_log.pcodenk).to eq(nil)
+ expect(sales_log.postcode_full).to eq(nil)
+ expect(sales_log.address_line1).to eq(nil)
+ expect(sales_log.address_line2).to eq(nil)
+ expect(sales_log.town_or_city).to eq(nil)
+ expect(sales_log.la).to eq(nil)
+ end
+ end
+ end
+end
diff --git a/spec/requests/duplicate_logs_controller_spec.rb b/spec/requests/duplicate_logs_controller_spec.rb
index 700964fcf..c2c05e748 100644
--- a/spec/requests/duplicate_logs_controller_spec.rb
+++ b/spec/requests/duplicate_logs_controller_spec.rb
@@ -77,8 +77,8 @@ RSpec.describe DuplicateLogsController, type: :request do
end
it "displays check your answers for each log with correct questions where UPRN is given" do
- lettings_log.update!(uprn: "123", uprn_known: 1, uprn_confirmed: 1)
- duplicate_logs[0].update!(uprn: "123", uprn_known: 1, uprn_confirmed: 1)
+ lettings_log.update!(uprn: "123", uprn_known: 1, uprn_confirmed: 1, manual_address_entry_selected: false)
+ duplicate_logs[0].update!(uprn: "123", uprn_known: 1, uprn_confirmed: 1, manual_address_entry_selected: false)
get "/lettings-logs/#{lettings_log.id}/duplicate-logs?original_log_id=#{lettings_log.id}"
expect(page).to have_content("Q5 - Tenancy start date", count: 3)
@@ -186,9 +186,9 @@ RSpec.describe DuplicateLogsController, type: :request do
end
it "displays check your answers for each log with correct questions when UPRN is given" do
- sales_log.update!(uprn: "123", uprn_known: 1)
- duplicate_logs[0].update!(uprn: "123", uprn_known: 1)
- duplicate_logs[1].update!(uprn: "123", uprn_known: 1)
+ sales_log.update!(uprn: "123", uprn_known: 1, manual_address_entry_selected: false)
+ duplicate_logs[0].update!(uprn: "123", uprn_known: 1, manual_address_entry_selected: false)
+ duplicate_logs[1].update!(uprn: "123", uprn_known: 1, manual_address_entry_selected: false)
get "/sales-logs/#{sales_log.id}/duplicate-logs?original_log_id=#{sales_log.id}"
expect(page).to have_content("Q1 - Sale completion date", count: 3)
diff --git a/spec/services/csv/sales_log_csv_service_spec.rb b/spec/services/csv/sales_log_csv_service_spec.rb
index 3cf56af2e..5e041b2d5 100644
--- a/spec/services/csv/sales_log_csv_service_spec.rb
+++ b/spec/services/csv/sales_log_csv_service_spec.rb
@@ -199,7 +199,7 @@ RSpec.describe Csv::SalesLogCsvService do
let(:fixed_time) { Time.zone.local(2024, 5, 1) }
before do
- log.update!(nationality_all: 36)
+ log.update!(nationality_all: 36, manual_address_entry_selected: false, uprn: "1", uprn_known: 1)
end
it "exports the CSV with the 2024 ordering and all values correct" do
@@ -286,6 +286,10 @@ RSpec.describe Csv::SalesLogCsvService do
let(:fixed_time) { Time.zone.local(2024, 5, 1) }
let(:year) { 2024 }
+ before do
+ log.update!(manual_address_entry_selected: false, uprn: "1", uprn_known: 1)
+ end
+
it "exports the CSV with all values correct" do
expected_content = CSV.read("spec/fixtures/files/sales_logs_csv_export_codes_24.csv")
values_to_delete = %w[ID]
@@ -338,7 +342,7 @@ RSpec.describe Csv::SalesLogCsvService do
let(:fixed_time) { Time.zone.local(2024, 5, 1) }
before do
- log.update!(nationality_all: 36)
+ log.update!(nationality_all: 36, manual_address_entry_selected: false, uprn: "1", uprn_known: 1)
end
context "and exporting with labels" do
diff --git a/spec/services/exports/lettings_log_export_service_spec.rb b/spec/services/exports/lettings_log_export_service_spec.rb
index 1db9cf4d9..12e3809f0 100644
--- a/spec/services/exports/lettings_log_export_service_spec.rb
+++ b/spec/services/exports/lettings_log_export_service_spec.rb
@@ -431,7 +431,7 @@ RSpec.describe Exports::LettingsLogExportService do
end
context "and one lettings log is available for export" do
- let!(:lettings_log) { FactoryBot.create(:lettings_log, :completed, assigned_to: user, age1: 35, sex1: "F", age2: 32, sex2: "M", ppostcode_full: "A1 1AA", nationality_all_group: 13, propcode: "123", postcode_full: "SE2 6RT", tenancycode: "BZ737", startdate: Time.zone.local(2024, 4, 2, 10, 36, 49), voiddate: Time.zone.local(2021, 11, 3), mrcdate: Time.zone.local(2022, 5, 5, 10, 36, 49), tenancylength: 5, underoccupation_benefitcap: 4, creation_method: 2, bulk_upload_id: 1, address_line1_as_entered: "address line 1 as entered", address_line2_as_entered: "address line 2 as entered", town_or_city_as_entered: "town or city as entered", county_as_entered: "county as entered", postcode_full_as_entered: "AB1 2CD", la_as_entered: "la as entered") }
+ let!(:lettings_log) { FactoryBot.create(:lettings_log, :completed, assigned_to: user, age1: 35, sex1: "F", age2: 32, sex2: "M", ppostcode_full: "A1 1AA", nationality_all_group: 13, propcode: "123", postcode_full: "SE2 6RT", tenancycode: "BZ737", startdate: Time.zone.local(2024, 4, 2, 10, 36, 49), voiddate: Time.zone.local(2021, 11, 3), mrcdate: Time.zone.local(2022, 5, 5, 10, 36, 49), tenancylength: 5, underoccupation_benefitcap: 4, creation_method: 2, bulk_upload_id: 1, address_line1_as_entered: "address line 1 as entered", address_line2_as_entered: "address line 2 as entered", town_or_city_as_entered: "town or city as entered", county_as_entered: "county as entered", postcode_full_as_entered: "AB1 2CD", la_as_entered: "la as entered", manual_address_entry_selected: false, uprn: "1", uprn_known: 1) }
let(:expected_zip_filename) { "core_2024_2025_apr_mar_f0001_inc0001.zip" }
let(:expected_data_filename) { "core_2024_2025_apr_mar_f0001_inc0001_pt001.xml" }
let(:xml_export_file) { File.open("spec/fixtures/exports/general_needs_log_24_25.xml", "r:UTF-8") }
diff --git a/spec/shared/shared_examples_for_derived_fields.rb b/spec/shared/shared_examples_for_derived_fields.rb
index 3e6b685df..3f746468a 100644
--- a/spec/shared/shared_examples_for_derived_fields.rb
+++ b/spec/shared/shared_examples_for_derived_fields.rb
@@ -25,11 +25,14 @@ RSpec.shared_examples "shared examples for derived fields" do |log_type|
end
it "does not affect older logs with uprn_confirmed == 0" do
- log = FactoryBot.build(log_type, uprn_known: 0, uprn: nil, uprn_confirmed: 0)
-
- expect { log.set_derived_fields! }.to not_change(log, :uprn_known)
- .and not_change(log, :uprn)
- .and not_change(log, :uprn_confirmed)
+ Timecop.freeze(Time.zone.local(2023, 4, 1)) do
+ log = FactoryBot.build(log_type, uprn_known: 0, uprn: nil, uprn_confirmed: 0)
+ allow(log.form).to receive(:start_year_2024_or_later?).and_return(false)
+ expect { log.set_derived_fields! }.to not_change(log, :uprn_known)
+ .and not_change(log, :uprn)
+ .and not_change(log, :uprn_confirmed)
+ end
+ Timecop.return
end
end
end
diff --git a/spec/shared/shared_log_examples.rb b/spec/shared/shared_log_examples.rb
index ef9ba32e6..77be654d7 100644
--- a/spec/shared/shared_log_examples.rb
+++ b/spec/shared/shared_log_examples.rb
@@ -81,7 +81,6 @@ RSpec.shared_examples "shared log examples" do |log_type|
expect { log.process_uprn_change! }.to change(log, :address_line1).from(nil).to("0, Building Name, Thoroughfare")
.and change(log, :town_or_city).from(nil).to("Posttown")
.and change(log, :postcode_full).from(nil).to("POSTCODE")
- .and change(log, :uprn_confirmed).from(1).to(nil)
.and change(log, :county).from("county").to(nil)
end
end
@@ -156,7 +155,6 @@ RSpec.shared_examples "shared log examples" do |log_type|
.and change(log, :uprn_confirmed).from(nil).to(1)
.and change(log, :uprn).from(nil).to("UPRN")
.and change(log, :uprn_known).from(nil).to(1)
- .and change(log, :uprn_selection).from("UPRN").to(nil)
.and change(log, :county).from("county").to(nil)
end
end