diff --git a/app/src/frontend/map/map.tsx b/app/src/frontend/map/map.tsx index 064fb5fe..4d7a5f1b 100644 --- a/app/src/frontend/map/map.tsx +++ b/app/src/frontend/map/map.tsx @@ -117,10 +117,12 @@ class ColouringMap extends Component { const baseLayer = ; const buildingsBaseUrl = `/tiles/base_${this.state.theme}/{z}/{x}/{y}{r}.png`; - const buildingBaseLayer = ; + const buildingBaseLayer = ; const boundaryStyleFn = () => ({color: '#bbb', fill: false}); @@ -146,6 +148,7 @@ class ColouringMap extends Component { key={tileset} url={`/tiles/${tileset}/{z}/{x}/{y}{r}.png?rev=${rev}`} minZoom={9} + maxZoom={19} /> : null; @@ -154,7 +157,8 @@ class ColouringMap extends Component { : null; @@ -167,7 +171,7 @@ class ColouringMap extends Component { center={position} zoom={this.state.zoom} minZoom={9} - maxZoom={18} + maxZoom={19} doubleClickZoom={false} zoomControl={false} attributionControl={false} diff --git a/app/src/frontend/pages/contact.tsx b/app/src/frontend/pages/contact.tsx index 5106437a..eb6fb99e 100644 --- a/app/src/frontend/pages/contact.tsx +++ b/app/src/frontend/pages/contact.tsx @@ -9,14 +9,25 @@ const ContactPage = () => (

Colouring London has been designed as a sustainable, low-cost model for knowledge exchange/open data platforms able to be reproduced by other towns and cities using our open platform code.

-

It is being developed by a small, dedicated team at UCL. We are unable to answer individual queries but welcome constructive comments on how to improve the site, and on other types of data and new features you might like to see.​

+

It is being developed by a small, dedicated team at UCL. We are unable to answer individual queries but welcome constructive comments on how to improve the site, and on other types of data and new features you might like to see.

You can send us comments or ask questions on our discussion threads at https://discuss.colouring.london/.

- +

To view our technical site and platform code please visit Github at: https://github.com/tomalrussell/colouring-london.

-

For press enquiries please contact the Bartlett Press and Communications team at architecture@ucl.ac.uk.

+

For press enquiries please contact the Bartlett Press and Communications team at architecture@ucl.ac.uk

+

+ If you capture images from the maps on Colouring London, please credit our + contributors (who collected the data) and Ordnance Survey + (who provided the basemaps and building geometries) as follows: +

+

+


+            Colouring London https://colouring.london Building attribute data is © Colouring London contributors. Maps contain OS data © Crown copyright: OS Maps baselayers and building outlines.
+            
+

+

diff --git a/app/src/frontend/pages/data-extracts.tsx b/app/src/frontend/pages/data-extracts.tsx index 16021689..3482475f 100644 --- a/app/src/frontend/pages/data-extracts.tsx +++ b/app/src/frontend/pages/data-extracts.tsx @@ -1,8 +1,9 @@ import React, { FunctionComponent } from 'react'; -import { NavLink } from 'react-router-dom'; +import { Link } from 'react-router-dom'; import { dateReviver } from '../../helpers'; + interface ExtractViewModel { extract_id: number; extracted_on: Date; @@ -33,7 +34,7 @@ export default class DataExtracts extends React.Component<{}, DataExtractsState> .sort((a, b) => a.extracted_on.valueOf() - b.extracted_on.valueOf()) .reverse(); - + this.setState({ extracts: extracts, latestExtract: extracts[0], previousExtracts: extracts.slice(1) }); } @@ -44,8 +45,22 @@ export default class DataExtracts extends React.Component<{}, DataExtractsState>

Open data extracts

-

Choose one of the links below to download an archive containing the open data collected on the Colouring London platform

-

By downloading data extracts from this site, you agree to the data accuracy agreement and the Ordnance Survey terms of UPRN usage.

+

+ Choose one of the links below to download an archive containing the open data collected on the Colouring London platform +

+

+ Colouring London contributions are open data, licensed under the Open Data Commons Open Database License (ODbL) by Colouring London contributors. +

+

+ You are free to copy, distribute, transmit and adapt our data, as long as you credit Colouring London and our contributors. If you alter or build upon our data, you may distribute the result only under the same licence. +

+

+ Choose one of the links below to download an archive containing the open data collected on the Colouring London platform. +

+

+ By downloading data extracts from this site, you agree to the data accuracy agreement and the Ordnance Survey terms of UPRN usage. +

+ { this.state.extracts == undefined ?

Loading extracts...

: @@ -69,14 +84,14 @@ export default class DataExtracts extends React.Component<{}, DataExtractsState>

Older extracts

    { - this.state.previousExtracts.map(e => + this.state.previousExtracts.map(e =>
  • ) }
- ) : + ) : null } diff --git a/app/src/frontend/pages/welcome.tsx b/app/src/frontend/pages/welcome.tsx index 7d4bb04d..f2c99c4a 100644 --- a/app/src/frontend/pages/welcome.tsx +++ b/app/src/frontend/pages/welcome.tsx @@ -17,11 +17,18 @@ const Welcome = () => ( volunteers of all ages and abilities to test and provide feedback on the site as we build it.

+

+ All of the data we collect is made openly available – + please read our data ethics policy and + credit Colouring London if you use or share our maps or data. +

Start Colouring Here! +

Colouring London collaborating organisations: The Bartlett UCL, Ordnance Survey, Historic England, Greater London Authority +

); diff --git a/app/src/frontend/user/my-account.tsx b/app/src/frontend/user/my-account.tsx index dc8f6630..b4676fbc 100644 --- a/app/src/frontend/user/my-account.tsx +++ b/app/src/frontend/user/my-account.tsx @@ -107,11 +107,17 @@ class MyAccountPage extends Component {

Welcome, {this.props.user.username}!

- Colouring London is under active development, Please discuss + Colouring London is under active development. Please discuss suggestions for improvements and report issues or problems. +

+

+ For reference, here are the privacy policy, contributor agreement and data accuracy agreement.

diff --git a/app/src/tiles/rendererDefinition.ts b/app/src/tiles/rendererDefinition.ts index 2ae4d086..bacfe6f3 100644 --- a/app/src/tiles/rendererDefinition.ts +++ b/app/src/tiles/rendererDefinition.ts @@ -29,7 +29,7 @@ const tileCache = new TileCache( { tilesets: getBuildingLayerNames(), minZoom: 9, - maxZoom: 18, + maxZoom: 19, scales: [1, 2] }, diff --git a/etl/join_building_data/load_csv_to_staging.py b/etl/join_building_data/load_csv_to_staging.py new file mode 100644 index 00000000..413cd533 --- /dev/null +++ b/etl/join_building_data/load_csv_to_staging.py @@ -0,0 +1,109 @@ +"""Join csv data to buildings +Example usage (replace URL with test/staging/localhost as necessary, API key with real key for +the appropriate site): + python load_csv_to_staging.py \ + https://clstaging.casa.ucl.ac.uk \ + a0a00000-0a00-0aaa-a0a0-0000aaaa0000 \ + data.csv +This script uses the HTTP API, and can process CSV files which identify buildings by id, TOID, +UPRN. +The process: + - assume first line of the CSV is a header, where column names are either + - building identifiers - one of: + - building_id + - toid + - uprn + - building data field names + - read through lines of CSV: + - use building id if provided + - else lookup by toid + - else lookup by uprn + - else locate building by representative point + - update building +TODO extend to allow latitude,longitude or easting,northing columns and lookup by location. +""" +import csv +import json +import os +import sys + +import requests +session = requests.Session() +session.verify = False + +def main(base_url, api_key, source_file): + """Read from file, update buildings + """ + with open(source_file, 'r') as source: + reader = csv.DictReader(source) + for line in reader: + building_id = find_building(line, base_url) + + if building_id is None: + continue + + response_code, response_data = update_building(building_id, line, api_key, base_url) + if response_code != 200: + print('ERROR', building_id, response_code, response_data) + + +def update_building(building_id, data, api_key, base_url): + """Save data to a building + """ + r = requests.post( + "{}/api/buildings/{}.json".format(base_url, building_id), + params={'api_key': api_key}, + json=data, + verify=False + ) + print(r) + return r.status_code, r.json() + + +def find_building(data, base_url): + if 'toid' in data: + building_id = find_by_reference(base_url, 'toid', data['toid']) + if building_id is not None: + print("match_by_toid", data['toid'], building_id) + return building_id + + if 'uprn' in data: + building_id = find_by_reference(base_url, 'uprn', data['uprn']) + if building_id is not None: + print("match_by_uprn", data['uprn'], building_id) + return building_id + + print("no_match", data) + return None + + +def find_by_reference(base_url, ref_key, ref_id): + """Find building_id by TOID or UPRN + """ + r = requests.get("{}/api/buildings/reference".format(base_url), params={ + 'key': ref_key, + 'id': ref_id, + }, + verify=False + ) + buildings = r.json() + + if buildings and 'error' not in buildings and len(buildings) == 1: + building_id = buildings[0]['building_id'] + else: + building_id = None + + return building_id + + +if __name__ == '__main__': + try: + url, api_key, filename = sys.argv[1], sys.argv[2], sys.argv[3] + except IndexError: + print( + "Usage: {} ./path/to/data.csv".format( + os.path.basename(__file__) + )) + exit() + + main(url, api_key, filename)