#!/usr/bin/env python3 """ convert_cities.py BoopLabs Pupmap Europe/Nordics Cities GeoJSON Version: 2025-10-03 """ import geopandas as gpd # ---------- User paths ---------- cities_shp = "ne_10m_populated_places.shp" output_dir = "/mnt/storage/docker-data/pupmap/www/data/" # ---------- Europe + Nordics ISO3 ---------- europe_nordics = [ 'ALB','AND','AUT','BEL','BIH','BGR','HRV','CYP','CZE','DNK','EST','FIN','FRA','DEU', 'GRC','HUN','ISL','IRL','ITA','LVA','LTU','LUX','MLT','MDA','MCO','MNE','NLD','NOR', 'POL','PRT','ROU','RUS','SMR','SRB','SVK','SVN','ESP','SWE','CHE','UKR','GBR','VAT' ] # ---------- Load cities shapefile ---------- print("Processing cities...") cities = gpd.read_file(cities_shp) # Filter Europe/Nordics if 'ADM0_A3' in cities.columns: cities_filtered = cities[cities['ADM0_A3'].isin(europe_nordics)].copy() else: cities_filtered = cities.copy() # fallback: include all # Rename columns to match map expectations cities_filtered = cities_filtered.rename(columns={ 'NAME': 'name', 'ADM0NAME': 'country', 'POP_MAX': 'population' }) # Keep only required columns cities_filtered = cities_filtered[['name','country','population','geometry']] # Save to GeoJSON cities_geojson_path = output_dir + "world_cities_europe.geojson" cities_filtered.to_file(cities_geojson_path, driver='GeoJSON') print(f"Saved {cities_geojson_path} ({len(cities_filtered)} features)")