From 7b8b4226c9c8a167a6c6a79993fd5fce163f9670 Mon Sep 17 00:00:00 2001 From: Tom Russell Date: Thu, 25 Oct 2018 14:36:52 +0100 Subject: [PATCH] Show UPRNs in building view - add /building/id/uprns.json endpoint - hide children behind details [Closes #83] --- app/src/building.js | 14 +++++++-- app/src/frontend/app.js | 21 ++++++++++++- app/src/frontend/building-view.js | 46 +++++++++++++++++++++++++++-- app/src/frontend/fields-config.json | 2 +- app/src/frontend/sidebar.css | 4 +++ app/src/server.js | 25 ++++++++++++++-- 6 files changed, 104 insertions(+), 8 deletions(-) diff --git a/app/src/building.js b/app/src/building.js index 0be8da41..bf2de7eb 100644 --- a/app/src/building.js +++ b/app/src/building.js @@ -83,6 +83,16 @@ function getBuildingById(id) { }); } +function getBuildingUPRNsById(id) { + return db.any( + "SELECT uprn, parent_uprn FROM building_properties WHERE building_id = $1", + [id] + ).catch(function(error){ + console.error(error); + return undefined; + }); +} + function saveBuilding(building_id, building, user_id) { // save building could fail if the revision seen by the user != the latest revision // - any 'intuitive' retries would need to be handled by clients of this code @@ -244,5 +254,5 @@ function compare(old_obj, new_obj, whitelist){ return [forward_patch, reverse_patch] } -export { queryBuildingsAtPoint, queryBuildingsByReference, getBuildingById, saveBuilding, - likeBuilding }; +export { queryBuildingsAtPoint, queryBuildingsByReference, getBuildingById, + getBuildingUPRNsById, saveBuilding, likeBuilding }; diff --git a/app/src/frontend/app.js b/app/src/frontend/app.js index 5566becf..1049970a 100644 --- a/app/src/frontend/app.js +++ b/app/src/frontend/app.js @@ -51,7 +51,26 @@ class App extends React.Component { } selectBuilding(building) { - this.setState({building: building}) + // get UPRNs and update + fetch(`/building/${building.building_id}/uprns.json`, { + method: 'GET', + headers:{ + 'Content-Type': 'application/json' + }, + credentials: 'same-origin' + }).then( + res => res.json() + ).then((res) => { + if (res.error) { + console.error(res); + } else { + building.uprns = res.uprns; + this.setState({building: building}); + } + }).catch((err) => { + console.error(err) + this.setState({building: building}); + }); } render() { diff --git a/app/src/frontend/building-view.js b/app/src/frontend/building-view.js index d5b992e5..da989616 100644 --- a/app/src/frontend/building-view.js +++ b/app/src/frontend/building-view.js @@ -31,13 +31,19 @@ const BuildingView = (props) => { building_id={props.building_id} {...section_props}> { - section_props.fields.map(field_props => ( + section_props.fields.map(field_props => { + return (field_props.slug === 'uprns')? + + : - )) + }) } )) @@ -101,4 +107,40 @@ const DataEntry = (props) => ( ); +const UPRNsDataEntry = (props) => { + const uprns = props.value || []; + const no_parent = uprns.filter(uprn => uprn.parent_uprn == null); + const with_parent = uprns.filter(uprn => uprn.parent_uprn != null); + + return ( + +
+ { props.title } + { props.tooltip? : null } +
+
    + { + no_parent.length? + no_parent.map(uprn => ( +
  • {uprn.uprn}
  • + )) + : '\u00A0' + }
    + { + with_parent.length? +
    + Children + { + with_parent.map(uprn => ( +
  • {uprn.uprn} (child of {uprn.parent_uprn})
  • + )) + } +
    + : null + } +
+
+ ) +} + export default BuildingView; diff --git a/app/src/frontend/fields-config.json b/app/src/frontend/fields-config.json index 62cdde54..132c65a2 100644 --- a/app/src/frontend/fields-config.json +++ b/app/src/frontend/fields-config.json @@ -20,7 +20,7 @@ "disabled": true }, { - "title": "UPRNs", "slug": "ref_uprn", "type": "list", + "title": "UPRNs", "slug": "uprns", "type": "list", "tooltip": "Unique Property Reference Numbers (to be filled automatically)", "disabled": true }, diff --git a/app/src/frontend/sidebar.css b/app/src/frontend/sidebar.css index 9ca07c69..6fd8bf2f 100644 --- a/app/src/frontend/sidebar.css +++ b/app/src/frontend/sidebar.css @@ -258,3 +258,7 @@ .data-list .no-data { color: #999; } +.data-list dd ul { + list-style: none; + padding-left: 0; +} diff --git a/app/src/server.js b/app/src/server.js index d2a079ed..f03e69da 100644 --- a/app/src/server.js +++ b/app/src/server.js @@ -18,7 +18,7 @@ import App from './frontend/app'; import db from './db'; import { authUser, createUser, getUserById, authAPIUser, getNewUserAPIKey } from './user'; import { queryBuildingsAtPoint, queryBuildingsByReference, getBuildingById, - saveBuilding, likeBuilding } from './building'; + getBuildingUPRNsById, saveBuilding, likeBuilding } from './building'; import tileserver from './tileserver'; import { parseBuildingURL } from './parse'; @@ -76,15 +76,20 @@ function frontendRoute(req, res) { Promise.all([ req.session.user_id? getUserById(req.session.user_id) : undefined, - is_building? getBuildingById(building_id) : undefined + is_building? getBuildingById(building_id) : undefined, + is_building? getBuildingUPRNsById(building_id) : undefined ]).then(function(values){ const user = values[0]; const building = values[1]; + const uprns = values[2]; if (is_building && typeof(building) === "undefined"){ context.status = 404 } data.user = user; data.building = building; + if (data.building != null) { + data.building.uprns = uprns + } renderHTML(context, data, req, res) }).catch(error => { console.error(error); @@ -218,6 +223,22 @@ function updateBuilding(req, res, user_id){ ) } +server.get('/building/:building_id/uprns.json', function (req, res) { + const { building_id } = req.params; + getBuildingUPRNsById(building_id).then(function(result){ + if (typeof(result) === "undefined") { + res.send({error:'Database error'}) + return + } + res.send({ + uprns: result + }); + }).catch(function(error){ + console.error(error); + res.send({error:'Database error'}) + }) + }) + // POST like building server.post('/building/like/:building_id', function(req, res){ if (!req.session.user_id) {