Skip to content
HAv5.0
Patterns

Validation

How to keep bad data out of a product without slowing down the person adding good data. Drawn from Spotta, where every review belongs to one of 1,590 street records.

The rule

Check data before it goes live. When the system isn’t sure, it flags, and a person decides.

Before and after

Shown with a sample street
OSM boundary · IkejaAllen Avenuerecord 1OSM boundary · OpebiAllen Avenuerecord 2
Before · on demandSaved when first reviewedStreets came from OpenStreetMap and were saved the first time someone reviewed one. But OSM put the same street under different areas depending on the boundary, so one street could become two records.
IkejaAllen Avenue1 record, 1 pageFlagged resolved imported
After · checked firstChecked before it existsDuplicates are flagged and resolved before import. Each street gets one record and one page, and the live site only ever sees clean data.

Where the checks run

  1. Source

    OpenStreetMap

    Free and open. Google’s Places API cost too much at city scale.

  2. Flag

    Duplicate check

    A tool I built with AI scans the data and flags streets that appear across boundary zones.

    Machine
  3. Decide

    Manual resolution

    I settle each flagged pair, then export the clean data to XLSX.

    Person
  4. Import

    Admin dashboard

    Bulk upload. The system validates every row and generates the URL slugs.

    Machine

The tool is fast at finding candidates. Whether two records are one street needs someone who knows the area. What came out the other end is live today: 1,590 streets across 28 neighbourhoods.

Try it

Bring the sheet in, settle the flags, then import
Bulk import · no sheet yetAdmin dashboard
  1. Upload
  2. Review
  3. Import
On your desktop
Drop streets.xlsx hereIt’s in the folder just above. Five streets, two of them need a decision.
No sheet yet. Drop one in to start.

What gets checked

CheckWhenFound byDecided by
Same street under two areasBefore importThe duplicate toolMe
Missing name, area or LGAOn importThe admin dashboardWhoever is importing
URL slugOn importThe admin dashboardNobody. It’s generated.

Rules

Do
  • Check records before they go live, not after people have started using them.
  • Let the machine find candidates. Let a person make the call.
  • Name the row and the field: “Row 4: LGA is missing.”
  • Generate what can be generated. Slugs are never typed.
Don’t
  • Merge on a name match alone. Two streets in one city can share a name.
  • Report “1 error” without saying where it is.
  • Let half-checked data reach the live site.