From 0adbc7af8cd01f27ccb0960bac0fa79838d8915e Mon Sep 17 00:00:00 2001 From: Roman Stolar Date: Thu, 9 Jan 2025 15:07:13 +0200 Subject: [PATCH 01/16] WIP --- .../actions/contributeProductionLocation.js | 1106 +---------------- .../SearchByNameAndAddressResult.jsx | 13 +- src/react/src/util/util.js | 16 + 3 files changed, 40 insertions(+), 1095 deletions(-) diff --git a/src/react/src/actions/contributeProductionLocation.js b/src/react/src/actions/contributeProductionLocation.js index cc09f2178..560e78a69 100644 --- a/src/react/src/actions/contributeProductionLocation.js +++ b/src/react/src/actions/contributeProductionLocation.js @@ -4,6 +4,7 @@ import apiRequest from '../util/apiRequest'; import { logErrorAndDispatchFailure, makeGetProductionLocationByOsIdURL, + makeGetProductionLocationsForSearchMatches, } from '../util/util'; export const startFetchSingleProductionLocation = createAction( @@ -52,1102 +53,23 @@ export function fetchProductionLocationByOsId(osID) { }; } -// TODO: Remove mockedProductionLocations after implementation of an actual -// API call as part of https://opensupplyhub.atlassian.net/browse/OSDEV-1374 -const mockedProductionLocations = { - count: 50, - data: [ - { - sector: ['Apparel'], - location_type: ['Contractor', 'Logo Application'], - name: 'Robinson Manufacturing Company Dayton Very Long Name', - parent_company: 'Robinson', - claim_status: 'unclaimed', - number_of_workers: { - max: 53, - min: 53, - }, - product_type: ['Accessories', 'Decoration'], - coordinates: { - lat: 35.4872298, - lng: -85.0189463, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '798 Market Street, Dayton, Dayton, Tennessee 37321', - os_id: 'US2019085AACCK0', - processing_type: ['Contractor', 'Logo Application'], - }, - { - sector: ['Apparel'], - location_type: ['Finished Goods'], - name: 'Robinson Manufacturing Company, Dayton', - parent_company: 'ROBINSON', - claim_status: 'unclaimed', - number_of_workers: { - max: 58, - min: 58, - }, - product_type: ['APPAREL', 'NIKE'], - coordinates: { - lat: 35.5118656, - lng: -85.0064775, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '1184 Broadway Dayton Tennessee 37321', - os_id: 'US2022082XJ6DVN', - processing_type: ['Finished Goods'], - }, - { - sector: ['Consumer Products', 'General Merchandise'], - location_type: ['Manufacturing', 'Production', 'Logo Application'], - name: 'Robinson Manufacturing', - claim_status: 'unclaimed', - product_type: [ - 'Accessories', - 'Loungewear', - 'Sleepwear', - 'Underwear', - ], - coordinates: { - lat: 35.4872298, - lng: -85.0189463, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '798 S. Market Street, Dayton, Tennessee, 37321, United States', - os_id: 'US2024275MWQQ62', - processing_type: [ - 'Manufacturing', - 'Production', - 'Logo Application', - ], - }, - { - sector: ['Agriculture', 'Farming'], - name: 'GRUBER MANUFACTURING, INC', - claim_status: 'unclaimed', - coordinates: { - lat: 39.6900755, - lng: -121.8560144, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '2462 Dayton Road, CHICO, CA, 95928-8225', - os_id: 'US2024299KEN8HK', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'CPCA MANUFACTURING LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 39.762, - lng: -84.227, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '750 ROSEDALE DR, DAYTON OHIO 45402 (MONTGOMERY)', - os_id: 'US2024212DV02QP', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Apparel', 'Apparel Accessories'], - name: 'E T Manufacturing & Sales, Inc.', - claim_status: 'unclaimed', - coordinates: { - lat: 40.8727141, - lng: -74.1177198, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '90 Dayton Ave, Passaic, NJ, 07055', - os_id: 'US2024275HE0B6E', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Offsite Chemical Disposal', - 'Onsite Chemical Disposal', - ], - name: 'HOHMAN PLATING & MANUFACTURING INC', - claim_status: 'unclaimed', - coordinates: { - lat: 39.784, - lng: -84.185, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '814 HILLROSE AVE, DAYTON OHIO 45404 (MONTGOMERY)', - os_id: 'US2024212GE5H1A', - processing_type: [ - 'Offsite Chemical Disposal', - 'Onsite Chemical Disposal', - ], - }, - { - sector: ['Health', 'Medical Equipment & Services'], - name: 'GEM City Enginnering and Manufacturing Corporation', - claim_status: 'unclaimed', - coordinates: { - lat: 39.7842949, - lng: -84.1911605, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '401 Leo St Dayton, Ohio 45404', - os_id: 'US2024283CJQHGK', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'MAYDAY MANUFACTURING CO', - claim_status: 'unclaimed', - coordinates: { - lat: 33.22, - lng: -97.174, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '3100 JIM CHRISTAL RD, DENTON TEXAS 76207 (DENTON)', - os_id: 'US2024213ZB3ZHK', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Health', 'Healthcare', 'Pharmaceuticals'], - name: 'Kobayashi America Manufacturing, LLC', - parent_company: 'Kobayashi Consumer Products LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 34.7045473, - lng: -84.9496968, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '245 Kraft Dr Dalton, Georgia 30721', - os_id: 'US2023084VCWT7Z', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - name: - 'GLOBAL TUBING LLC COILED TUBING MANUFACTURING FACILITY IN DA', - claim_status: 'unclaimed', - coordinates: { - lat: 30.023, - lng: -94.904, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '501 CR 493, DAYTON TEXAS 77535 (LIBERTY)', - os_id: 'US2024213M0RG2M', - }, - { - sector: ['Manufacturing'], - name: 'CF MANUFACTURING LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 29.1883701, - lng: -81.0338419, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '828 S nova rd, daytona beach, FL, 32114-5802', - os_id: 'US2024294RSD344', - }, - { - sector: ['Manufacturing'], - name: 'RUT MANUFACTURING, INC.', - claim_status: 'unclaimed', - coordinates: { - lat: 35.5659544, - lng: -80.09753839999999, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '22650 HWY 109, DENTON, NC 27239', - os_id: 'US2024302BWQVJ0', - }, - { - sector: ['Waste Management'], - location_type: ['RCRAInfo subtitle C (Hazardous waste handlers)'], - name: 'ALADDIN MANUFACTURING CORP - MCFARLAND RD', - claim_status: 'unclaimed', - coordinates: { - lat: 34.72919, - lng: -84.96658, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '104 MCFARLAND RD, DALTON, GA, 30721', - os_id: 'US202427424D36S', - processing_type: ['RCRAInfo subtitle C (Hazardous waste handlers)'], - }, - { - sector: ['Health', 'Medical Equipment & Services'], - name: 'Product Quest Manufacturing LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 29.2313552, - lng: -81.03630100000001, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '330 Carswell Ave Daytona Beach, Florida 32117', - os_id: 'US2024284HFGCME', - }, - { - sector: ['Apparel'], - location_type: ['Logo Application', 'Contractor'], - name: 'CROWN MANUFACTURING', - historical_os_id: ['US20190853PWY1N', 'US20203490X4Q5S'], - claim_status: 'unclaimed', - number_of_workers: { - max: 71, - min: 71, - }, - coordinates: { - lat: 35.2102754, - lng: -89.7832442, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '8390 WOLF LAKE DRIVE BARTLETT TENNESSEE 38133', - os_id: 'US20242498JW7NH', - processing_type: ['Logo Application', 'Contractor'], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'BTD MANUFACTURING INC.', - claim_status: 'unclaimed', - coordinates: { - lat: 34.359, - lng: -84.051, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '55 IMPULSE DR, DAWSONVILLE GEORGIA 30534 (DAWSON)', - os_id: 'US2024213RVKAGP', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'SCHAEFFER MANUFACTURING', - claim_status: 'unclaimed', - coordinates: { - lat: 38.6, - lng: -90.199, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '102 BARTON ST, SAINT LOUIS MISSOURI 63104 (ST LOUIS (CITY))', - os_id: 'US20242120TZ4P8', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Food'], - name: 'Buchanan Manufacturing, Inc.', - claim_status: 'unclaimed', - coordinates: { - lat: 36.382747, - lng: -88.222516, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '575 Cowpath Rd Buchanan, Tennessee 38222', - os_id: 'US2024284RA1K9X', - }, - { - sector: ['Metal Manufacturing'], - name: 'APEX MANUFACTURING GROUP INC.', - claim_status: 'unclaimed', - coordinates: { - lat: 39.6522694, - lng: -75.7258085, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '825 Dawson Drive Ste 1, Newark, DE, 19713', - os_id: 'US2024292N604QK', - }, - { - sector: ['Equipment', 'Manufacturing'], - name: 'JACKSON CREEK MANUFACTURING INC.', - claim_status: 'unclaimed', - coordinates: { - lat: 35.6187618, - lng: -80.08854439999999, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '206 Bingham Industrial Dr., DENTON, NC 27239-7795', - os_id: 'US2024302F2292K', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - name: 'ORTHMAN MANUFACTURING INC NORTH PLANT', - claim_status: 'unclaimed', - coordinates: { - lat: 40.81, - lng: -99.711, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '75765 RD 435, LEXINGTON NEBRASKA 68850 (DAWSON)', - os_id: 'US2024213T818RS', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'CLOROX PRODUCTS MANUFACTURING', - claim_status: 'unclaimed', - coordinates: { - lat: 33.627, - lng: -84.391, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '115 LAKE MIRROR RD, FOREST PARK GEORGIA 30297 (CLAYTON)', - os_id: 'US20242132MFEPZ', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Apparel'], - name: 'Wise Manufacturing, Inc', - claim_status: 'unclaimed', - coordinates: { - lat: 36.2646365, - lng: -86.67173249999999, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '645 Old Hickory Blvd. Nashville Tennessee 37138', - os_id: 'US2020254R737MM', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'SCHICK MANUFACTURING INC', - claim_status: 'unclaimed', - coordinates: { - lat: 35.959, - lng: -83.828, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '2820 MEDIA DR, KNOXVILLE TENNESSEE 37914 (KNOX)', - os_id: 'US202421339SE09', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Offsite Chemical Disposal', - 'Onsite Chemical Disposal', - ], - name: 'BATESVILLE MANUFACTURING LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 35.498, - lng: -86.072, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '175 MONOGARD DR, MANCHESTER TENNESSEE 37355 (COFFEE)', - os_id: 'US20242127SXDVT', - processing_type: [ - 'Offsite Chemical Disposal', - 'Onsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'MODINE MANUFACTURING CO', - claim_status: 'unclaimed', - coordinates: { - lat: 35.266, - lng: -87.329, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '2009 REMKE AVE, LAWRENCEBURG TENNESSEE 38464 (LAWRENCE)', - os_id: 'US2024213H2KNN6', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Offsite Chemical Disposal', - 'Onsite Chemical Disposal', - ], - name: 'TAG MANUFACTURING INC.', - claim_status: 'unclaimed', - coordinates: { - lat: 35.076, - lng: -85.15, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '6989 DISCOVERY DR., CHATTANOOGA TENNESSEE 37416 (HAMILTON)', - os_id: 'US20242136X89CP', - processing_type: [ - 'Offsite Chemical Disposal', - 'Onsite Chemical Disposal', - ], - }, - { - sector: ['Health', 'Healthcare', 'Pharmaceuticals'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'Iatric Manufacturing Solutions, LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 36.2425997, - lng: -83.21361069999999, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '328 Hamblen Ave Morristown, Tennessee 37813', - os_id: 'US2024213TGT532', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Food'], - location_type: ['Confectionery Merchant Wholesalers'], - name: 'Wrigley Manufacturing Company, LLC', - claim_status: 'unclaimed', - product_type: ['Confectionery'], - coordinates: { - lat: 35.0575, - lng: -85.19637700000001, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '3002 Jersey Pike Chattanooga, Tennessee 37421', - os_id: 'US202424494DHFM', - processing_type: ['Confectionery Merchant Wholesalers'], - }, - { - sector: ['Health', 'Medical Equipment & Services'], - name: 'Valley Manufacturing Co Inc', - claim_status: 'unclaimed', - coordinates: { - lat: 35.8973921, - lng: -86.8720665, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '104 Beta Dr Franklin, Tennessee 37064', - os_id: 'US2024286AFYPT7', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'PIOLAX MANUFACTURING PLANT EXPANSION', - claim_status: 'unclaimed', - coordinates: { - lat: 34.247, - lng: -84.472, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '140 ETOWAH INDUSTRIAL CT, CANTON GEORGIA 30114 (CHEROKEE)', - os_id: 'US2024212BWK8E5', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'POLARTEC TENNESSEE MANUFACTURING', - parent_company: 'Polartec, LLC', - claim_status: 'unclaimed', - product_type: ['Materials Manufacturing'], - coordinates: { - lat: 35.133, - lng: -84.903, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '310 INDUSTRIAL DR SW, CLEVELAND TENNESSEE 37311 (BRADLEY)', - os_id: 'US2019083XFE7PP', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'LODGE MANUFACTURING CO', - claim_status: 'unclaimed', - coordinates: { - lat: 35.008, - lng: -85.706, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '600 RAILROAD AVENUE, SOUTH PITTSBURG TENNESSEE 37380 (MARION)', - os_id: 'US20242135BDJ49', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'RAVAGO MANUFACTURING AMERICAS', - claim_status: 'unclaimed', - coordinates: { - lat: 35.437, - lng: -86.025, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '405 PARK TOWER DR, MANCHESTER TENNESSEE 37355 (COFFEE)', - os_id: 'US2024213QKT0VN', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Offsite Chemical Disposal', - 'Onsite Chemical Disposal', - ], - name: 'IBC MANUFACTURING CO', - claim_status: 'unclaimed', - coordinates: { - lat: 35.063, - lng: -90.078, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '416 E BROOKS RD, MEMPHIS TENNESSEE 38109 (SHELBY)', - os_id: 'US20242136SY670', - processing_type: [ - 'Offsite Chemical Disposal', - 'Onsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - name: 'MANUFACTURING SCIENCES CORP', - claim_status: 'unclaimed', - coordinates: { - lat: 36.004, - lng: -84.232, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '804 S ILLINOIS AVE, OAK RIDGE TENNESSEE 37830 (ANDERSON)', - os_id: 'US20242131D840G', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'OSHKOSH MANUFACTURING LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 36.107, - lng: -83.495, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '1400 FLAT GAP RD, JEFFERSON CITY TENNESSEE 37760 (JEFFERSON)', - os_id: 'US2024213ES9NJD', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'WABTEC MANUFACTURING SOLUTIONS LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 33.029, - lng: -97.302, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '16201 THREE WIDE DR, FORT WORTH TEXAS 76177 (DENTON)', - os_id: 'US202421385TFP2', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Food'], - name: 'Memphis Pyramid Barbecue Sauce Manufacturing Co', - claim_status: 'unclaimed', - coordinates: { - lat: 35.0575559, - lng: -89.3036889, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '19600 Highway 57 Moscow, Tennessee 38057', - os_id: 'US2024283947FPP', - }, - { - sector: ['Forestry', 'Wood Products'], - name: 'SOUTHERN TIMBER EXTRACTS MANUFACTURING CO., INC', - claim_status: 'unclaimed', - coordinates: { - lat: 30.723197, - lng: -88.07836170000002, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '542 BARTON ST S, MOBILE, AL, 36610-4740', - os_id: 'US2024300WEAJMD', - }, - { - sector: ['Apparel'], - name: 'Eagle Manufacturing Co.', - claim_status: 'unclaimed', - coordinates: { - lat: 36.1953095, - lng: -86.78789739999999, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '230 Cumberland Bend, Nashville, Tennessee, United States of America', - os_id: 'US2020133EPKZDP', - }, - { - sector: ['Health', 'Medical Equipment & Services'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'Denso Manufacturing Tennessee, Inc', - claim_status: 'unclaimed', - coordinates: { - lat: 35.7620477, - lng: -84.0033316, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '1720 Robert C Jackson Dr Maryville, Tennessee 37801', - os_id: 'US2024212J3HQM6', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'SILGAN CONTAINERS MANUFACTURING CORP', - claim_status: 'unclaimed', - coordinates: { - lat: 35.96, - lng: -88.95, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '1226 S MANUFACTURERS ROW, TRENTON TENNESSEE 38382 (GIBSON)', - os_id: 'US20242124FQ414', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - name: 'VESTAL MANUFACTURING ENTERPRISES INC.', - claim_status: 'unclaimed', - coordinates: { - lat: 35.605, - lng: -84.454, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: - '177 INDUSTRIAL PARK RD, SWEETWATER TENNESSEE 37874 (MONROE)', - os_id: 'US2024213ATXCX0', - }, - { - sector: ['Chemicals', 'Commodities', 'Waste Management'], - location_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - name: 'DENSO MANUFACTURING ATHENS TENNESSEE INC', - claim_status: 'unclaimed', - coordinates: { - lat: 35.474, - lng: -84.644, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '2400 2406 2408 DENSO DR, ATHENS TENNESSEE 37303 (MCMINN)', - os_id: 'US2024212G2QAV3', - processing_type: [ - 'Onsite Chemical Disposal', - 'Offsite Chemical Disposal', - ], - }, - { - sector: ['Tobacco Products'], - name: 'A.C.E. Manufacturing, LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 42.3616725, - lng: -87.8309903, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '119 N Genesee St Waukegan, Illinois 60085', - os_id: 'US2024280P32ENR', - }, - { - sector: ['Health', 'Medical Equipment & Services'], - name: 'Big River Engineering and Manufacturing', - claim_status: 'unclaimed', - coordinates: { - lat: 35.1462187, - lng: -90.0468369, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '85 N 4th St Memphis, Tennessee 38103', - os_id: 'US2024281FXYVBB', - }, - { - sector: ['Health', 'Medical Equipment & Services'], - name: 'Eaton Manufacturing Corporation Dba Eaton Medical', - parent_company: 'Eaton Manufacturing Corporation', - claim_status: 'unclaimed', - coordinates: { - lat: 35.1235658, - lng: -90.01545349999999, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '1401 Heistan Pl Memphis, Tennessee 38104', - os_id: 'US202428635MMXD', - }, - { - sector: ['Food'], - name: 'St. Lawrence County Manufacturing and Properties, LLC', - claim_status: 'unclaimed', - coordinates: { - lat: 44.5896342, - lng: -75.173701, - }, - country: { - name: 'United States', - numeric: '840', - alpha_3: 'USA', - alpha_2: 'US', - }, - address: '30 Buck St Canton, New York 13617', - os_id: 'US2024286MWYBMD', - }, - ], -}; - -export function fetchProductionLocations() { +export function fetchProductionLocations(data) { return async dispatch => { dispatch(startFetchProductionLocations()); - // TODO: Replace the mock implementation with an actual API call - // as part of https://opensupplyhub.atlassian.net/browse/OSDEV-1374 - return new Promise(resolve => { - setTimeout( - () => resolve({ data: mockedProductionLocations }), - 1000, - ); - }) - .then(({ data }) => - dispatch(completeFetchProductionLocations(data)), + const { name, address, country } = data; + + return apiRequest + .get( + makeGetProductionLocationsForSearchMatches( + name, + address, + country, + ), ) + .then(response => { + dispatch(completeFetchProductionLocations(response.data)); + }) .catch(err => dispatch( logErrorAndDispatchFailure( diff --git a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx index 08858bdff..a17ed4e70 100644 --- a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx +++ b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx @@ -1,5 +1,6 @@ import React, { useEffect } from 'react'; import { arrayOf, bool, func, number, object } from 'prop-types'; +import { useLocation } from 'react-router-dom'; import CircularProgress from '@material-ui/core/CircularProgress'; import { withStyles } from '@material-ui/core/styles'; import { connect } from 'react-redux'; @@ -23,9 +24,15 @@ const SearchByNameAndAddressResult = ({ clearLocations, classes, }) => { + const location = useLocation(); + useEffect(() => { - fetchLocations(); - }, [fetchLocations]); + const searchParams = new URLSearchParams(location.search); + const name = searchParams.get('name'); + const address = searchParams.get('address'); + const country = searchParams.get('country'); + fetchLocations({ name, address, country }); + }, [location.search, fetchLocations]); const handleBackToSearchByNameAddress = () => { clearLocations(); @@ -80,7 +87,7 @@ const mapStateToProps = ({ fetching, }); const mapDispatchToProps = dispatch => ({ - fetchLocations: () => dispatch(fetchProductionLocations()), + fetchLocations: data => dispatch(fetchProductionLocations(data)), clearLocations: () => dispatch(resetProductionLocations()), }); diff --git a/src/react/src/util/util.js b/src/react/src/util/util.js index 8089e4054..1100bd8a0 100644 --- a/src/react/src/util/util.js +++ b/src/react/src/util/util.js @@ -260,6 +260,22 @@ export const makeNonStandardFieldsURL = () => '/api/nonstandard-fields/'; export const makeGetProductionLocationByOsIdURL = osID => `/api/v1/production-locations/${osID}/`; +export const makeGetProductionLocationsForSearchMatches = ( + name, + address, + country, + osId, +) => { + const params = new URLSearchParams(); + + if (name) params.append('name', name); + if (address) params.append('address', address); + if (country) params.append('country', country); + if (osId) params.append('search_after[id]', osId); + + return `/api/v1/production-locations/?${params.toString()}`; +}; + export const makeGetModerationEventsWithQueryString = ( qs, page, From 72b7624769bc0c65c2328f85086fc9da950f6e0e Mon Sep 17 00:00:00 2001 From: Roman Stolar Date: Fri, 10 Jan 2025 16:01:34 +0200 Subject: [PATCH 02/16] IN PROGRESS --- src/react/src/actions/contributeProductionLocation.js | 3 ++- .../Contribute/SearchByNameAndAddressResult.jsx | 8 +++++--- .../Contribute/SearchByNameAndAddressSuccessResult.jsx | 8 ++++++++ src/react/src/util/util.js | 4 ++-- 4 files changed, 17 insertions(+), 6 deletions(-) diff --git a/src/react/src/actions/contributeProductionLocation.js b/src/react/src/actions/contributeProductionLocation.js index 560e78a69..c311b625f 100644 --- a/src/react/src/actions/contributeProductionLocation.js +++ b/src/react/src/actions/contributeProductionLocation.js @@ -57,7 +57,7 @@ export function fetchProductionLocations(data) { return async dispatch => { dispatch(startFetchProductionLocations()); - const { name, address, country } = data; + const { name, address, country, fromIndex } = data; return apiRequest .get( @@ -65,6 +65,7 @@ export function fetchProductionLocations(data) { name, address, country, + fromIndex, ), ) .then(response => { diff --git a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx index a17ed4e70..5bc3a22fc 100644 --- a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx +++ b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx @@ -1,4 +1,4 @@ -import React, { useEffect } from 'react'; +import React, { useEffect, useState } from 'react'; import { arrayOf, bool, func, number, object } from 'prop-types'; import { useLocation } from 'react-router-dom'; import CircularProgress from '@material-ui/core/CircularProgress'; @@ -25,14 +25,15 @@ const SearchByNameAndAddressResult = ({ classes, }) => { const location = useLocation(); + const [fromIndex, setFromIndex] = useState(10); useEffect(() => { const searchParams = new URLSearchParams(location.search); const name = searchParams.get('name'); const address = searchParams.get('address'); const country = searchParams.get('country'); - fetchLocations({ name, address, country }); - }, [location.search, fetchLocations]); + fetchLocations({ name, address, country, fromIndex }); + }, [location.search, fromIndex, fetchLocations]); const handleBackToSearchByNameAddress = () => { clearLocations(); @@ -60,6 +61,7 @@ const SearchByNameAndAddressResult = ({ productionLocations={productionLocations} productionLocationsCount={productionLocationsCount} clearLocations={clearLocations} + setFromIndex={setFromIndex} /> ) : ( diff --git a/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx b/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx index df4edd359..12a00da30 100644 --- a/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx +++ b/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx @@ -12,6 +12,7 @@ const SearchByNameAndAddressSuccessResult = ({ productionLocationsCount, productionLocations, clearLocations, + setFromIndex, classes, }) => { const [confirmDialogIsOpen, setConfirmDialogIsOpen] = useState(false); @@ -31,6 +32,12 @@ const SearchByNameAndAddressSuccessResult = ({ }; }, []); + useEffect(() => { + if (isScrolledToBottom) { + setFromIndex(productionLocations.length + 10); + } + }, [isScrolledToBottom]); + const handleSelectLocation = () => {}; const handleNotFoundLocation = () => { @@ -127,6 +134,7 @@ SearchByNameAndAddressSuccessResult.propTypes = { productionLocationsCount: number.isRequired, productionLocations: arrayOf(productionLocationPropType).isRequired, clearLocations: func.isRequired, + setFromIndex: func.isRequired, classes: object.isRequired, }; diff --git a/src/react/src/util/util.js b/src/react/src/util/util.js index 7ce694214..97361aca8 100644 --- a/src/react/src/util/util.js +++ b/src/react/src/util/util.js @@ -275,14 +275,14 @@ export const makeGetProductionLocationsForSearchMatches = ( name, address, country, - osId, + fromIndex, ) => { const params = new URLSearchParams(); if (name) params.append('name', name); if (address) params.append('address', address); if (country) params.append('country', country); - if (osId) params.append('search_after[id]', osId); + if (fromIndex) params.append('size', fromIndex); return `/api/v1/production-locations/?${params.toString()}`; }; From ad88310dd1d85c9ca7b26f12bf5ee1c31f0a61f4 Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Mon, 13 Jan 2025 15:14:57 +0100 Subject: [PATCH 03/16] set up routing, added task description --- doc/release/RELEASE-NOTES.md | 5 ++++- .../ConfirmNotFoundLocationDialog.jsx | 6 +++++- .../Contribute/ProductionLocationInfo.jsx | 5 +++-- .../SearchByNameAndAddressNotFoundResult.jsx | 9 +++++---- .../SearchByNameAndAddressResult.jsx | 3 ++- .../SearchByNameAndAddressSuccessResult.jsx | 18 ++++++++++++++++-- 6 files changed, 35 insertions(+), 11 deletions(-) diff --git a/doc/release/RELEASE-NOTES.md b/doc/release/RELEASE-NOTES.md index 9d12ce215..cd2fcb0b3 100644 --- a/doc/release/RELEASE-NOTES.md +++ b/doc/release/RELEASE-NOTES.md @@ -28,7 +28,7 @@ This project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html - Connected PATCH `/v1/moderation-events/{moderation_id}/` (for Reject button). - Connected POST `/v1/moderation-events/{moderation_id}/production-locations/` (for Create New Location button). - Connected PATCH `/v1/moderation-events/{moderation_id}/production-locations/{os_id}/` (for Confirm potential match button). - - UI improvements: + - UI improvements: - Added a toast component to display notifications during moderation event updates. - Introduced a backdrop to prevent accidental clicks on other buttons during the update process. - Applied Django Signal for moderation-events OpenSearch index. @@ -37,6 +37,9 @@ This project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html * Successful Search: If the search is successful, the results screen displays a list of production locations. Each item includes the following information about the production location: name, OS ID, address, and country name. Users can either select a specific production location or press the "I don’t see my Location" button, which triggers a confirmation dialog window. * Confirmation Dialog Window: In this window, users can confirm that no correct location was found using the provided search parameters. They can either proceed to create a new production location or return to the search. * Unsuccessful Search: If the search is unsuccessful, an explanation is provided along with two options: return to the search or add a new production location. +* [OSDEV-1374](https://opensupplyhub.atlassian.net/browse/OSDEV-1374) - Implemented integration of search & result page for name and address search (`/contribute/production-location/search`): + - Connected GET `v1/production-locations`. + - Routing between pages `Production Location Search`,`Search returned no results`, `Production Location Information`, `Search results`, and `I don't see my Location` pop-up is configured. ### Release instructions: * Ensure that the following commands are included in the `post_deployment` command: diff --git a/src/react/src/components/Contribute/ConfirmNotFoundLocationDialog.jsx b/src/react/src/components/Contribute/ConfirmNotFoundLocationDialog.jsx index 9cef6b1a1..987679e43 100644 --- a/src/react/src/components/Contribute/ConfirmNotFoundLocationDialog.jsx +++ b/src/react/src/components/Contribute/ConfirmNotFoundLocationDialog.jsx @@ -10,7 +10,10 @@ import CloseIcon from '@material-ui/icons/Close'; import Typography from '@material-ui/core/Typography'; import history from '../../util/history'; import { makeConfirmNotFoundLocationDialogStyles } from '../../util/styles'; -import { contributeProductionLocationRoute } from '../../util/constants'; +import { + contributeProductionLocationRoute, + productionLocationInfoRoute, +} from '../../util/constants'; const ConfirmNotFoundLocationDialog = ({ confirmDialogIsOpen, @@ -21,6 +24,7 @@ const ConfirmNotFoundLocationDialog = ({ const handleAddNewLocation = () => { handleConfirmDialogClose(); clearLocations(); + history.push(productionLocationInfoRoute); }; const navigateToNameAddressTab = () => { diff --git a/src/react/src/components/Contribute/ProductionLocationInfo.jsx b/src/react/src/components/Contribute/ProductionLocationInfo.jsx index 0178f14d2..e277da657 100644 --- a/src/react/src/components/Contribute/ProductionLocationInfo.jsx +++ b/src/react/src/components/Contribute/ProductionLocationInfo.jsx @@ -1,5 +1,5 @@ import React, { useEffect, useState } from 'react'; -import { useLocation } from 'react-router-dom'; +import { useLocation, useHistory } from 'react-router-dom'; import { withStyles } from '@material-ui/core/styles'; import { func, object } from 'prop-types'; import { connect } from 'react-redux'; @@ -56,6 +56,7 @@ const ProductionLocationInfo = ({ const [numberOfWorkers, setNumberOfWorkers] = useState(''); const [parentCompany, setParentCompany] = useState([]); const customSelectComponents = { DropdownIndicator: null }; + const history = useHistory(); const selectStyles = { control: provided => ({ @@ -476,7 +477,7 @@ const ProductionLocationInfo = ({
diff --git a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx index 5bc3a22fc..60ceae72a 100644 --- a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx +++ b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx @@ -10,6 +10,7 @@ import { } from '../../actions/contributeProductionLocation'; import BackToSearchButton from './BackToSearchButton'; import SearchByNameAndAddressNotFoundResult from './SearchByNameAndAddressNotFoundResult'; + import SearchByNameAndAddressSuccessResult from './SearchByNameAndAddressSuccessResult'; import { contributeProductionLocationRoute } from '../../util/constants'; import history from '../../util/history'; @@ -37,7 +38,7 @@ const SearchByNameAndAddressResult = ({ const handleBackToSearchByNameAddress = () => { clearLocations(); - history.push(`${contributeProductionLocationRoute}?tab=name-address`); + history.push(`${contributeProductionLocationRoute}?tab=name-address`); // here change }; if (fetching) { diff --git a/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx b/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx index 12a00da30..74f0a7ee6 100644 --- a/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx +++ b/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx @@ -1,4 +1,5 @@ import React, { useEffect, useState } from 'react'; +import { useHistory } from 'react-router-dom'; import { arrayOf, func, number, object } from 'prop-types'; import Button from '@material-ui/core/Button'; import { withStyles } from '@material-ui/core/styles'; @@ -7,6 +8,7 @@ import { makeSearchByNameAndAddressSuccessResultStyles } from '../../util/styles import { productionLocationPropType } from '../../util/propTypes'; import ConfirmNotFoundLocationDialog from './ConfirmNotFoundLocationDialog'; import ProductionLocationDetails from './ProductionLocationDetails'; +import { productionLocationInfoRoute } from '../../util/constants'; const SearchByNameAndAddressSuccessResult = ({ productionLocationsCount, @@ -17,6 +19,7 @@ const SearchByNameAndAddressSuccessResult = ({ }) => { const [confirmDialogIsOpen, setConfirmDialogIsOpen] = useState(false); const [isScrolledToBottom, setIsScrolledToBottom] = useState(false); + const history = useHistory(); useEffect(() => { const handleScroll = () => { @@ -38,7 +41,18 @@ const SearchByNameAndAddressSuccessResult = ({ } }, [isScrolledToBottom]); - const handleSelectLocation = () => {}; + const handleSelectLocation = location => { + const { name, address, country } = location; + const baseUrl = productionLocationInfoRoute; + const params = new URLSearchParams({ + name, + address, + country: country.alpha_2, + }); + const url = `${baseUrl}?${params.toString()}`; + + history.push(url); + }; const handleNotFoundLocation = () => { setConfirmDialogIsOpen(true); @@ -93,7 +107,7 @@ const SearchByNameAndAddressSuccessResult = ({ />
); } - return ( <>
@@ -62,7 +63,6 @@ const SearchByNameAndAddressResult = ({ productionLocations={productionLocations} productionLocationsCount={productionLocationsCount} clearLocations={clearLocations} - setFromIndex={setFromIndex} /> ) : ( diff --git a/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx b/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx index 74f0a7ee6..b6fa47d7c 100644 --- a/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx +++ b/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx @@ -8,13 +8,15 @@ import { makeSearchByNameAndAddressSuccessResultStyles } from '../../util/styles import { productionLocationPropType } from '../../util/propTypes'; import ConfirmNotFoundLocationDialog from './ConfirmNotFoundLocationDialog'; import ProductionLocationDetails from './ProductionLocationDetails'; -import { productionLocationInfoRoute } from '../../util/constants'; +import { + productionLocationInfoRoute, + MAX_LOCATIONS_TO_SHOW, +} from '../../util/constants'; const SearchByNameAndAddressSuccessResult = ({ productionLocationsCount, productionLocations, clearLocations, - setFromIndex, classes, }) => { const [confirmDialogIsOpen, setConfirmDialogIsOpen] = useState(false); @@ -35,12 +37,6 @@ const SearchByNameAndAddressSuccessResult = ({ }; }, []); - useEffect(() => { - if (isScrolledToBottom) { - setFromIndex(productionLocations.length + 10); - } - }, [isScrolledToBottom]); - const handleSelectLocation = location => { const { name, address, country } = location; const baseUrl = productionLocationInfoRoute; @@ -87,7 +83,10 @@ const SearchByNameAndAddressSuccessResult = ({
- {productionLocationsCount} results + {productionLocationsCount > MAX_LOCATIONS_TO_SHOW + ? MAX_LOCATIONS_TO_SHOW + : productionLocationsCount}{' '} + results Sort By: Best match @@ -148,7 +147,6 @@ SearchByNameAndAddressSuccessResult.propTypes = { productionLocationsCount: number.isRequired, productionLocations: arrayOf(productionLocationPropType).isRequired, clearLocations: func.isRequired, - setFromIndex: func.isRequired, classes: object.isRequired, }; diff --git a/src/react/src/util/constants.jsx b/src/react/src/util/constants.jsx index 7d3c25e37..3d112ef76 100644 --- a/src/react/src/util/constants.jsx +++ b/src/react/src/util/constants.jsx @@ -1507,3 +1507,5 @@ export const mockedSectors = [ ['Pets', 'Pets'], ['Packaging', 'Packaging'], ]; + +export const MAX_LOCATIONS_TO_SHOW = 100; diff --git a/src/react/src/util/util.js b/src/react/src/util/util.js index 97361aca8..708c1ac7e 100644 --- a/src/react/src/util/util.js +++ b/src/react/src/util/util.js @@ -275,14 +275,14 @@ export const makeGetProductionLocationsForSearchMatches = ( name, address, country, - fromIndex, + limit, ) => { const params = new URLSearchParams(); if (name) params.append('name', name); if (address) params.append('address', address); if (country) params.append('country', country); - if (fromIndex) params.append('size', fromIndex); + if (limit) params.append('size', limit); return `/api/v1/production-locations/?${params.toString()}`; }; From aef17d8e3f53bb923e7c8da2791d753ec2b2731c Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Tue, 14 Jan 2025 12:05:00 +0100 Subject: [PATCH 05/16] corrected small issue --- doc/release/RELEASE-NOTES.md | 4 ++-- .../components/Contribute/SearchByNameAndAddressResult.jsx | 1 - 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/doc/release/RELEASE-NOTES.md b/doc/release/RELEASE-NOTES.md index c714cb936..5d20467ec 100644 --- a/doc/release/RELEASE-NOTES.md +++ b/doc/release/RELEASE-NOTES.md @@ -37,10 +37,10 @@ This project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html * Successful Search: If the search is successful, the results screen displays a list of production locations. Each item includes the following information about the production location: name, OS ID, address, and country name. Users can either select a specific production location or press the "I don’t see my Location" button, which triggers a confirmation dialog window. * Confirmation Dialog Window: In this window, users can confirm that no correct location was found using the provided search parameters. They can either proceed to create a new production location or return to the search. * Unsuccessful Search: If the search is unsuccessful, an explanation is provided along with two options: return to the search or add a new production location. -* [OSDEV-1374](https://opensupplyhub.atlassian.net/browse/OSDEV-1374) - Implemented integration of search & result page for name and address search (`/contribute/production-location/search`): +* [OSDEV-1374](https://opensupplyhub.atlassian.net/browse/OSDEV-1374) - Implemented integration for the `Search results` page to show results of searching by name and address (`/contribute/production-location/search`): - Connected GET `v1/production-locations`. - Routing between pages `Production Location Search`,`Search returned no results`, `Production Location Information`, `Search results`, and `I don't see my Location` pop-up is configured. - - Max result limit set to 100 + - Max result limit set to 100. ### Release instructions: * Ensure that the following commands are included in the `post_deployment` command: diff --git a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx index b9805f792..d7e1bb9d2 100644 --- a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx +++ b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx @@ -10,7 +10,6 @@ import { } from '../../actions/contributeProductionLocation'; import BackToSearchButton from './BackToSearchButton'; import SearchByNameAndAddressNotFoundResult from './SearchByNameAndAddressNotFoundResult'; - import SearchByNameAndAddressSuccessResult from './SearchByNameAndAddressSuccessResult'; import { contributeProductionLocationRoute, From 0d0ec290f9c89341af7ed9bc371187619f2dbe63 Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Wed, 15 Jan 2025 17:27:24 +0100 Subject: [PATCH 06/16] delete redundant productionLocationsCount --- .../Contribute/SearchByNameAndAddressResult.jsx | 10 +++------- .../SearchByNameAndAddressSuccessResult.jsx | 14 +++----------- .../ContributeProductionLocationReducer.js | 3 --- 3 files changed, 6 insertions(+), 21 deletions(-) diff --git a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx index d7e1bb9d2..28ecbc583 100644 --- a/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx +++ b/src/react/src/components/Contribute/SearchByNameAndAddressResult.jsx @@ -1,5 +1,5 @@ import React, { useEffect } from 'react'; -import { arrayOf, bool, func, number, object } from 'prop-types'; +import { arrayOf, bool, func, object } from 'prop-types'; import { useLocation } from 'react-router-dom'; import CircularProgress from '@material-ui/core/CircularProgress'; import { withStyles } from '@material-ui/core/styles'; @@ -21,7 +21,6 @@ import { makeSearchByNameAndAddressResultStyles } from '../../util/styles'; const SearchByNameAndAddressResult = ({ data: productionLocations, - count: productionLocationsCount, fetching, fetchLocations, clearLocations, @@ -57,10 +56,9 @@ const SearchByNameAndAddressResult = ({ handleBackToSearch={handleBackToSearchByNameAddress} />
- {productionLocationsCount > 0 ? ( + {productionLocations.length > 0 ? ( ) : ( @@ -72,7 +70,6 @@ const SearchByNameAndAddressResult = ({ SearchByNameAndAddressResult.propTypes = { data: arrayOf(productionLocationPropType).isRequired, - count: number.isRequired, fetching: bool.isRequired, fetchLocations: func.isRequired, clearLocations: func.isRequired, @@ -81,11 +78,10 @@ SearchByNameAndAddressResult.propTypes = { const mapStateToProps = ({ contributeProductionLocation: { - productionLocations: { data, count, fetching }, + productionLocations: { data, fetching }, }, }) => ({ data, - count, fetching, }); const mapDispatchToProps = dispatch => ({ diff --git a/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx b/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx index b6fa47d7c..ff44c5383 100644 --- a/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx +++ b/src/react/src/components/Contribute/SearchByNameAndAddressSuccessResult.jsx @@ -1,6 +1,6 @@ import React, { useEffect, useState } from 'react'; import { useHistory } from 'react-router-dom'; -import { arrayOf, func, number, object } from 'prop-types'; +import { arrayOf, func, object } from 'prop-types'; import Button from '@material-ui/core/Button'; import { withStyles } from '@material-ui/core/styles'; import Typography from '@material-ui/core/Typography'; @@ -8,13 +8,9 @@ import { makeSearchByNameAndAddressSuccessResultStyles } from '../../util/styles import { productionLocationPropType } from '../../util/propTypes'; import ConfirmNotFoundLocationDialog from './ConfirmNotFoundLocationDialog'; import ProductionLocationDetails from './ProductionLocationDetails'; -import { - productionLocationInfoRoute, - MAX_LOCATIONS_TO_SHOW, -} from '../../util/constants'; +import { productionLocationInfoRoute } from '../../util/constants'; const SearchByNameAndAddressSuccessResult = ({ - productionLocationsCount, productionLocations, clearLocations, classes, @@ -83,10 +79,7 @@ const SearchByNameAndAddressSuccessResult = ({
- {productionLocationsCount > MAX_LOCATIONS_TO_SHOW - ? MAX_LOCATIONS_TO_SHOW - : productionLocationsCount}{' '} - results + {productionLocations.length} results Sort By: Best match @@ -144,7 +137,6 @@ const SearchByNameAndAddressSuccessResult = ({ }; SearchByNameAndAddressSuccessResult.propTypes = { - productionLocationsCount: number.isRequired, productionLocations: arrayOf(productionLocationPropType).isRequired, clearLocations: func.isRequired, classes: object.isRequired, diff --git a/src/react/src/reducers/ContributeProductionLocationReducer.js b/src/react/src/reducers/ContributeProductionLocationReducer.js index 2bc83e05a..49dcadd8b 100644 --- a/src/react/src/reducers/ContributeProductionLocationReducer.js +++ b/src/react/src/reducers/ContributeProductionLocationReducer.js @@ -18,7 +18,6 @@ const initialState = Object.freeze({ error: null, }), productionLocations: Object.freeze({ - count: 0, data: [], fetching: false, error: null, @@ -72,7 +71,6 @@ export default createReducer( productionLocations: { fetching: { $set: true }, error: { $set: initialState.productionLocations.error }, - count: { $set: initialState.productionLocations.count }, data: { $set: initialState.productionLocations.data }, }, }), @@ -92,7 +90,6 @@ export default createReducer( $set: initialState.productionLocations.fetching, }, error: { $set: initialState.productionLocations.error }, - count: { $set: payload.count }, data: { $set: payload.data }, }, }), From b74e5327f2ff7703108145c5740cc55341f9bf95 Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Thu, 16 Jan 2025 09:39:15 +0100 Subject: [PATCH 07/16] merge two similar functions to one makeGetProductionLocationsForPotentialMatches --- .../actions/contributeProductionLocation.js | 4 ++-- .../actions/dashboardContributionRecord.js | 4 ++-- src/react/src/util/util.js | 20 +++---------------- 3 files changed, 7 insertions(+), 21 deletions(-) diff --git a/src/react/src/actions/contributeProductionLocation.js b/src/react/src/actions/contributeProductionLocation.js index 7e05f04da..709feeaeb 100644 --- a/src/react/src/actions/contributeProductionLocation.js +++ b/src/react/src/actions/contributeProductionLocation.js @@ -4,7 +4,7 @@ import apiRequest from '../util/apiRequest'; import { logErrorAndDispatchFailure, makeGetProductionLocationByOsIdURL, - makeGetProductionLocationsForSearchMatches, + makeGetProductionLocationsForPotentialMatches, } from '../util/util'; export const startFetchSingleProductionLocation = createAction( @@ -61,7 +61,7 @@ export function fetchProductionLocations(data) { return apiRequest .get( - makeGetProductionLocationsForSearchMatches( + makeGetProductionLocationsForPotentialMatches( name, address, country, diff --git a/src/react/src/actions/dashboardContributionRecord.js b/src/react/src/actions/dashboardContributionRecord.js index 43a45ef3f..138838941 100644 --- a/src/react/src/actions/dashboardContributionRecord.js +++ b/src/react/src/actions/dashboardContributionRecord.js @@ -99,16 +99,16 @@ export function fetchPotentialMatches(data) { const { productionLocationName, - countryCode, productionLocationAddress, + countryCode, } = data; return apiRequest .get( makeGetProductionLocationsForPotentialMatches( productionLocationName, - countryCode, productionLocationAddress, + countryCode, ), ) .then(potentialMatches => { diff --git a/src/react/src/util/util.js b/src/react/src/util/util.js index 708c1ac7e..e94073896 100644 --- a/src/react/src/util/util.js +++ b/src/react/src/util/util.js @@ -259,29 +259,15 @@ export const makeNonStandardFieldsURL = () => '/api/nonstandard-fields/'; export const makeGetProductionLocationsForPotentialMatches = ( productionLocationName, - countryCode, - address, -) => { - const params = new URLSearchParams(); - - if (productionLocationName) params.append('name', productionLocationName); - if (countryCode) params.append('country', countryCode); - if (address) params.append('address', address); - - return `/api/v1/production-locations/?${params.toString()}/`; -}; - -export const makeGetProductionLocationsForSearchMatches = ( - name, address, - country, + countryCode, limit, ) => { const params = new URLSearchParams(); - if (name) params.append('name', name); + if (productionLocationName) params.append('name', productionLocationName); if (address) params.append('address', address); - if (country) params.append('country', country); + if (countryCode) params.append('country', countryCode); if (limit) params.append('size', limit); return `/api/v1/production-locations/?${params.toString()}`; From 230fb92ebda6fd9b4814b7f79d7093301cd97326 Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Thu, 16 Jan 2025 15:06:56 +0100 Subject: [PATCH 08/16] added tests for Search Results page integratoin --- src/django/api/tests/test_search_results.py | 79 +++++++++++++++++++++ 1 file changed, 79 insertions(+) create mode 100644 src/django/api/tests/test_search_results.py diff --git a/src/django/api/tests/test_search_results.py b/src/django/api/tests/test_search_results.py new file mode 100644 index 000000000..d026750f7 --- /dev/null +++ b/src/django/api/tests/test_search_results.py @@ -0,0 +1,79 @@ + +import unittest.mock +from rest_framework.test import APITestCase +from rest_framework import status +OPEN_SEARCH_SERVICE = "api.views.v1.production_locations.OpenSearchService" + + +class SearchResultsTest(APITestCase): + def setUp(self): + super().setUp() + self.name = 'CHANG+KNITTING+FACTORY' + self.address = 'TONGHU+ECONOMIC+DEVELOPMENT+ZONE,HUIZHOU%2C+CHINA' + self.county_alpha_2_code = 'CN' + self.name1 = 'test name' + self.address1 = 'test address' + self.county_alpha_2_code1 = 'AX' + + self.search_mock = unittest.mock.patch(OPEN_SEARCH_SERVICE).start() + self.search_index_mock = self.search_mock.return_value.search_index + self.search_results_response_mock = { + "count": 2, + "data": [ + { + "sector": [ + "Apparel" + ], + "coordinates": { + "lat": 23.082231, + "lng": 114.196658 + }, + "os_id": "CN2025016GP2VEJ", + "country": { + "alpha_2": "CN", + "alpha_3": "CHN", + "name": "China", + "numeric": "156" + }, + "claim_status": "unclaimed", + "address": "KIU HING ROAD, 2-12 TONGHU ECONOMIC DEVELOPMENT ZONE,HUIZHOU, CHINA", + "name": "XIN CHANG CHANG KNITTING FACTORY" + }, + { + "sector": [ + "Apparel" + ], + "coordinates": { + "lat": 30.607581, + "lng": 120.55107 + }, + "os_id": "CN2025016RHMQVG", + "country": { + "alpha_2": "CN", + "alpha_3": "CHN", + "name": "China", + "numeric": "156" + }, + "claim_status": "unclaimed", + "address": "No. 2 Industrial Area Economic Development Zone, Tongxiang Hangzhou, Zhejiang Province", + "name": "Tongxiang Miracle Knitting Factory Co. Ltd." + } + ], + } + + def get_url(self, name, address, county_code): + return f"/api/v1/production-locations/?name={name}&address={address}&country={county_code}" + + def test_receive_search_results_data(self): + self.search_index_mock.return_value = self.search_results_response_mock + api_res = self.client.get(self.get_url(self.name, self.address, self.county_alpha_2_code)) + self.assertEqual(api_res.status_code, status.HTTP_200_OK) + self.assertEqual(api_res.data, self.search_results_response_mock) + self.assertEqual(len(api_res.data.get("data")), api_res.data.get("count")) + + def test_get_search_results_not_found(self): + self.search_index_mock.return_value = {"data": [], "count": 0} + api_res = self.client.get(self.get_url(self.name1, self.address1, self.county_alpha_2_code1)) + self.assertEqual(api_res.status_code, status.HTTP_200_OK) + self.assertEqual(len(api_res.data.get("data")), 0) + self.assertEqual(api_res.data.get("count"), 0) From f87083d992d8a8d0473e25d3dd265e88805cf028 Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Thu, 16 Jan 2025 16:41:39 +0100 Subject: [PATCH 09/16] fixed linter --- src/django/api/tests/test_search_results.py | 16 ++++++++++------ 1 file changed, 10 insertions(+), 6 deletions(-) diff --git a/src/django/api/tests/test_search_results.py b/src/django/api/tests/test_search_results.py index d026750f7..66e416187 100644 --- a/src/django/api/tests/test_search_results.py +++ b/src/django/api/tests/test_search_results.py @@ -36,7 +36,7 @@ def setUp(self): "numeric": "156" }, "claim_status": "unclaimed", - "address": "KIU HING ROAD, 2-12 TONGHU ECONOMIC DEVELOPMENT ZONE,HUIZHOU, CHINA", + "address": "KIU HING ROAD, 2-12 TONGHU, CHINA", "name": "XIN CHANG CHANG KNITTING FACTORY" }, { @@ -55,25 +55,29 @@ def setUp(self): "numeric": "156" }, "claim_status": "unclaimed", - "address": "No. 2 Industrial Area Economic Development Zone, Tongxiang Hangzhou, Zhejiang Province", + "address": "No. 2 Industrial Area Economic, Zhejiang Province", "name": "Tongxiang Miracle Knitting Factory Co. Ltd." } ], } def get_url(self, name, address, county_code): - return f"/api/v1/production-locations/?name={name}&address={address}&country={county_code}" + return (f"/api/v1/production-locations/?name={name}&address={address}" + "&country={county_code}") def test_receive_search_results_data(self): self.search_index_mock.return_value = self.search_results_response_mock - api_res = self.client.get(self.get_url(self.name, self.address, self.county_alpha_2_code)) + api_res = self.client.get( + self.get_url(self.name, self.address, self.county_alpha_2_code)) self.assertEqual(api_res.status_code, status.HTTP_200_OK) self.assertEqual(api_res.data, self.search_results_response_mock) - self.assertEqual(len(api_res.data.get("data")), api_res.data.get("count")) + self.assertEqual(len(api_res.data.get("data")), + api_res.data.get("count")) def test_get_search_results_not_found(self): self.search_index_mock.return_value = {"data": [], "count": 0} - api_res = self.client.get(self.get_url(self.name1, self.address1, self.county_alpha_2_code1)) + api_res = self.client.get( + self.get_url(self.name1, self.address1, self.county_alpha_2_code1)) self.assertEqual(api_res.status_code, status.HTTP_200_OK) self.assertEqual(len(api_res.data.get("data")), 0) self.assertEqual(api_res.data.get("count"), 0) From 65fbe92e99cab8c52c2d8408eb313909d948c829 Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Thu, 16 Jan 2025 18:07:06 +0100 Subject: [PATCH 10/16] renamed vars --- src/django/api/tests/test_search_results.py | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/django/api/tests/test_search_results.py b/src/django/api/tests/test_search_results.py index 66e416187..46ba539d2 100644 --- a/src/django/api/tests/test_search_results.py +++ b/src/django/api/tests/test_search_results.py @@ -10,10 +10,10 @@ def setUp(self): super().setUp() self.name = 'CHANG+KNITTING+FACTORY' self.address = 'TONGHU+ECONOMIC+DEVELOPMENT+ZONE,HUIZHOU%2C+CHINA' - self.county_alpha_2_code = 'CN' + self.county_code = 'CN' self.name1 = 'test name' self.address1 = 'test address' - self.county_alpha_2_code1 = 'AX' + self.county_code1 = 'AX' self.search_mock = unittest.mock.patch(OPEN_SEARCH_SERVICE).start() self.search_index_mock = self.search_mock.return_value.search_index @@ -68,7 +68,7 @@ def get_url(self, name, address, county_code): def test_receive_search_results_data(self): self.search_index_mock.return_value = self.search_results_response_mock api_res = self.client.get( - self.get_url(self.name, self.address, self.county_alpha_2_code)) + self.get_url(self.name, self.address, self.county_code)) self.assertEqual(api_res.status_code, status.HTTP_200_OK) self.assertEqual(api_res.data, self.search_results_response_mock) self.assertEqual(len(api_res.data.get("data")), @@ -77,7 +77,7 @@ def test_receive_search_results_data(self): def test_get_search_results_not_found(self): self.search_index_mock.return_value = {"data": [], "count": 0} api_res = self.client.get( - self.get_url(self.name1, self.address1, self.county_alpha_2_code1)) + self.get_url(self.name1, self.address1, self.county_code1)) self.assertEqual(api_res.status_code, status.HTTP_200_OK) self.assertEqual(len(api_res.data.get("data")), 0) self.assertEqual(api_res.data.get("count"), 0) From a51ef8e6293c35828035bc3e60e1b2ec699b5b50 Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Thu, 16 Jan 2025 19:06:17 +0100 Subject: [PATCH 11/16] fixed url for request --- src/django/api/tests/test_search_results.py | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/django/api/tests/test_search_results.py b/src/django/api/tests/test_search_results.py index 46ba539d2..ba5db12c4 100644 --- a/src/django/api/tests/test_search_results.py +++ b/src/django/api/tests/test_search_results.py @@ -2,6 +2,7 @@ import unittest.mock from rest_framework.test import APITestCase from rest_framework import status + OPEN_SEARCH_SERVICE = "api.views.v1.production_locations.OpenSearchService" @@ -62,8 +63,9 @@ def setUp(self): } def get_url(self, name, address, county_code): - return (f"/api/v1/production-locations/?name={name}&address={address}" - "&country={county_code}") + baseUrl = "/api/v1/production-locations/" + params = f"?name={name}&address={address}&country={county_code}" + return baseUrl+params def test_receive_search_results_data(self): self.search_index_mock.return_value = self.search_results_response_mock From 1786e67e3a6867e0a23178849a01c9c65222e57c Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Thu, 16 Jan 2025 19:09:04 +0100 Subject: [PATCH 12/16] renamed vars --- src/django/api/tests/test_search_results.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/django/api/tests/test_search_results.py b/src/django/api/tests/test_search_results.py index ba5db12c4..c34a7c4cb 100644 --- a/src/django/api/tests/test_search_results.py +++ b/src/django/api/tests/test_search_results.py @@ -63,9 +63,9 @@ def setUp(self): } def get_url(self, name, address, county_code): - baseUrl = "/api/v1/production-locations/" - params = f"?name={name}&address={address}&country={county_code}" - return baseUrl+params + base_url = "/api/v1/production-locations/" + query_string = f"?name={name}&address={address}&country={county_code}" + return f"{base_url}?{query_string}" def test_receive_search_results_data(self): self.search_index_mock.return_value = self.search_results_response_mock From df069788575840e3e22bc06ed809bd87d50a6ed3 Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Fri, 17 Jan 2025 14:18:18 +0100 Subject: [PATCH 13/16] extend React tests for this flow --- .../components/ConfirmNotFoundLocationDialog.test.js | 5 ++++- .../SearchByNameAndAddressNotFoundResult.test.js | 11 ++++++++++- .../SearchByNameAndAddressSuccessResult.test.js | 11 +++++++++++ .../components/SearchByOsIdSuccessResult.test.js | 7 +++---- 4 files changed, 28 insertions(+), 6 deletions(-) diff --git a/src/react/src/__tests__/components/ConfirmNotFoundLocationDialog.test.js b/src/react/src/__tests__/components/ConfirmNotFoundLocationDialog.test.js index dd737dc30..c0f6446d7 100644 --- a/src/react/src/__tests__/components/ConfirmNotFoundLocationDialog.test.js +++ b/src/react/src/__tests__/components/ConfirmNotFoundLocationDialog.test.js @@ -2,7 +2,7 @@ import React from "react"; import renderWithProviders from "../../util/testUtils/renderWithProviders"; import ConfirmNotFoundLocationDialog from "../../components/Contribute/ConfirmNotFoundLocationDialog"; import history from "../../util/history"; -import { contributeProductionLocationRoute } from "../../util/constants"; +import { contributeProductionLocationRoute, productionLocationInfoRoute } from "../../util/constants"; jest.mock("../../util/history", () => ({ push: jest.fn(), @@ -72,6 +72,9 @@ describe("ConfirmNotFoundLocationDialog component", () => { expect(mockHandleConfirmDialogClose).toHaveBeenCalledTimes(1); expect(mockClearLocations).toHaveBeenCalledTimes(1); + expect(history.push).toHaveBeenCalledWith( + productionLocationInfoRoute, + ); }); test("closes the dialog when the close button is clicked", () => { diff --git a/src/react/src/__tests__/components/SearchByNameAndAddressNotFoundResult.test.js b/src/react/src/__tests__/components/SearchByNameAndAddressNotFoundResult.test.js index f4c73dbd3..e96b9f552 100644 --- a/src/react/src/__tests__/components/SearchByNameAndAddressNotFoundResult.test.js +++ b/src/react/src/__tests__/components/SearchByNameAndAddressNotFoundResult.test.js @@ -1,7 +1,7 @@ import React from 'react'; import { fireEvent } from '@testing-library/react'; import SearchByNameAndAddressNotFoundResult from '../../components/Contribute/SearchByNameAndAddressNotFoundResult'; -import { contributeProductionLocationRoute } from '../../util/constants'; +import { contributeProductionLocationRoute, productionLocationInfoRoute } from '../../util/constants'; import history from '../../util/history'; import renderWithProviders from '../../util/testUtils/renderWithProviders'; @@ -35,4 +35,13 @@ describe('SearchByNameAndAddressNotFoundResult component', () => { expect(history.push).toHaveBeenCalledWith(`${contributeProductionLocationRoute}?tab=name-address`); }); + + test("navigates to the contribute page when 'Add a new Location' is clicked", () => { + const { getByRole } = renderWithProviders(); + + const addNewLocation = getByRole('button', { name: 'Add a new Location' }); + fireEvent.click(addNewLocation); + + expect(history.push).toHaveBeenCalledWith(productionLocationInfoRoute); + }); }); diff --git a/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js b/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js index dd6abb59b..0c5689083 100644 --- a/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js +++ b/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js @@ -106,4 +106,15 @@ describe('SearchByNameAndAddressSuccessResult component', () => { expect(queryByText('Close Dialog')).not.toBeInTheDocument(); }); + + test('opens the "Production Location Information" page when the "Select" button is clicked', () => { + const { getAllByRole } = renderWithProviders(); + const selectButtons = getAllByRole('button', { name: /Select/i }); + + selectButtons.forEach(button => { + expect(button).toBeInTheDocument(); + fireEvent.click(button); + }); + }); + }); diff --git a/src/react/src/__tests__/components/SearchByOsIdSuccessResult.test.js b/src/react/src/__tests__/components/SearchByOsIdSuccessResult.test.js index b6060485c..b06dec9b6 100644 --- a/src/react/src/__tests__/components/SearchByOsIdSuccessResult.test.js +++ b/src/react/src/__tests__/components/SearchByOsIdSuccessResult.test.js @@ -1,6 +1,6 @@ import React from 'react'; import { fireEvent } from '@testing-library/react'; -import SearchByOsIdSuccessResult from '../../components/Contribute/SearchByOsIdSuccessResult'; +import SearchByOsIdSuccessResult from '../../components/Contribute/SearchByOsIdSuccessResult'; import renderWithProviders from '../../util/testUtils/renderWithProviders'; jest.mock('../../components/Contribute/SearchByOsIdResultActions', () => ({ @@ -57,14 +57,13 @@ describe('SearchByOsIdSuccessResult component', () => { expect(getByRole('button', { name: 'Yes, add data and claim' })).toBeInTheDocument(); }); - test('calls handleBackToSearchByNameAddress when the default button is clicked', () => { + test('calls handleBackToSearchByNameAddress when the default button is clicked', async () => { const { getByRole } = renderWithProviders(); - const backButton = getByRole('button', { name: 'No, search by name and address', }); - fireEvent.click(backButton); + fireEvent.click(backButton); expect(defaultProps.handleBackToSearchByNameAddress).toHaveBeenCalledTimes(1); }); }); From 0fb6c153ba606c8316844656f022053fcfc5cb0c Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Fri, 17 Jan 2025 14:31:31 +0100 Subject: [PATCH 14/16] added clearAllMocks and additional checks --- .../components/SearchByNameAndAddressNotFoundResult.test.js | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/react/src/__tests__/components/SearchByNameAndAddressNotFoundResult.test.js b/src/react/src/__tests__/components/SearchByNameAndAddressNotFoundResult.test.js index e96b9f552..29b24d373 100644 --- a/src/react/src/__tests__/components/SearchByNameAndAddressNotFoundResult.test.js +++ b/src/react/src/__tests__/components/SearchByNameAndAddressNotFoundResult.test.js @@ -9,6 +9,10 @@ jest.mock('../../util/history', () => ({ push: jest.fn(), })); +beforeEach(() => { + jest.clearAllMocks(); +}); + describe('SearchByNameAndAddressNotFoundResult component', () => { test('renders the not found message and buttons correctly', () => { const { getByText, getByRole } = renderWithProviders(); @@ -40,8 +44,10 @@ describe('SearchByNameAndAddressNotFoundResult component', () => { const { getByRole } = renderWithProviders(); const addNewLocation = getByRole('button', { name: 'Add a new Location' }); + expect(addNewLocation).toBeInTheDocument(); fireEvent.click(addNewLocation); expect(history.push).toHaveBeenCalledWith(productionLocationInfoRoute); + expect(history.push).toHaveBeenCalledTimes(1); }); }); From 8eafae2de462189d2aa4af4c94b2e7b37557cad3 Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Fri, 17 Jan 2025 15:46:01 +0100 Subject: [PATCH 15/16] renamed test regarding logic --- .../components/SearchByNameAndAddressSuccessResult.test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js b/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js index 0c5689083..61a3d2d4f 100644 --- a/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js +++ b/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js @@ -107,7 +107,7 @@ describe('SearchByNameAndAddressSuccessResult component', () => { expect(queryByText('Close Dialog')).not.toBeInTheDocument(); }); - test('opens the "Production Location Information" page when the "Select" button is clicked', () => { + test('the "Select" button is clicked', () => { const { getAllByRole } = renderWithProviders(); const selectButtons = getAllByRole('button', { name: /Select/i }); From f2fd7ea215b5fe1a37ca5c1e9dc785c098f8bc8e Mon Sep 17 00:00:00 2001 From: Inessa Druzhkova Date: Tue, 21 Jan 2025 11:42:29 +0100 Subject: [PATCH 16/16] added test for routing --- .../SearchByNameAndAddressSuccessResult.test.js | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js b/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js index 61a3d2d4f..211ab3370 100644 --- a/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js +++ b/src/react/src/__tests__/components/SearchByNameAndAddressSuccessResult.test.js @@ -2,6 +2,16 @@ import React from 'react'; import { fireEvent } from '@testing-library/react'; import SearchByNameAndAddressSuccessResult from '../../components/Contribute/SearchByNameAndAddressSuccessResult'; import renderWithProviders from '../../util/testUtils/renderWithProviders'; +import { productionLocationInfoRoute } from '../../util/constants'; + +const mockHistoryPush = jest.fn(); + +jest.mock('react-router-dom', () => ({ + ...jest.requireActual('react-router-dom'), + useHistory: () => ({ + push: mockHistoryPush, + }), +})); jest.mock('../../components/Contribute/ConfirmNotFoundLocationDialog', () => ({ __esModule: true, @@ -107,14 +117,14 @@ describe('SearchByNameAndAddressSuccessResult component', () => { expect(queryByText('Close Dialog')).not.toBeInTheDocument(); }); - test('the "Select" button is clicked', () => { + test('opens the "Production Location Information" page when the "Select" button is clicked', () => { const { getAllByRole } = renderWithProviders(); const selectButtons = getAllByRole('button', { name: /Select/i }); selectButtons.forEach(button => { expect(button).toBeInTheDocument(); fireEvent.click(button); + expect(mockHistoryPush).toHaveBeenCalledWith(expect.stringContaining(productionLocationInfoRoute)); }); }); - });