Clusters & markers
Field tables for every object in a response, plus the GeoJSON form.
Base URL https://api.offendersearch.appWhat a view can contain
| Array | Object | When |
|---|---|---|
clusters | A cluster: a count for a grid cell. | Zoom 3–12, and closer views that are too dense for pins. |
markers | A pin: one person at one address. | Zoom 13–14, with no name. |
markers | A named pin. | Zoom 15+. |
markers | A many-people pin: several people at one address. | From zoom 13. |
areas | An approximate-area pin: people known only to an area. | From zoom 13. |
Cluster
| Field | Meaning |
|---|---|
id | An id for the cluster. Use it as a key when you redraw. |
lat, lng | Where to draw it. |
count | People in the cluster. |
bbox | west,south,east,north: the extent of the people in the cluster. |
expansionZoom | Fit the map to bbox at this zoom and the cluster comes apart: into smaller clusters, pins, or one many-people pin. |
breakdown | The same four numbers as the view’s breakdown, for this cluster. |
A cluster never traps the user. People who share one address never split, so at its expansionZoom such a cluster becomes one pin with a count and a groupId.
Pin
At zoom 13–14 a pin is a position and nothing that identifies anyone.
"mode": "pins",
"markers": [
{
"id": "mk_Qa8…",
"lat": 39.96123, "lng": -82.99881,
"precision": "street",
"addressType": "home"
}
]| Field | Meaning |
|---|---|
id | The marker id, mk_…. Pass it to the records route. |
lat, lng | The registered address. |
precision | street for an exact street address. |
addressType | home, work, school or other. |
distanceMiles | Only with a radius request: the distance from the centre. |
A person with two mapped addresses, such as home and work, has two pins. total counts that person once.
Named pin
From zoom 15 each pin also carries a label and basic fields.
"mode": "markers",
"markers": [
{
"id": "mk_Zb3…",
"lat": 39.96123, "lng": -82.99881,
"precision": "street",
"addressType": "home",
"label": "Sample J. Tester",
"housingStatus": "housed",
"hasPhoto": true,
"registryState": "OH"
},
{
"id": null,
"lat": 39.9678, "lng": -83.0042,
"precision": "street",
"count": 12,
"groupId": "mg_8Uo…",
"members": [
{
"id": "mk_…",
"addressType": "home",
"label": "Sample S. Demo",
"housingStatus": null,
"hasPhoto": false
}
]
}
],
"areas": [
{
"lat": 39.969, "lng": -83.0114,
"count": 9,
"precision": "zip",
"label": "43215",
"groupId": "mg_X1G…"
}
]| Field | Meaning |
|---|---|
label | The first initial and last name, such as “J. Smith”. |
housingStatus | housed, homeless or incarcerated. null when the registry does not say. null does not mean housed. |
hasPhoto | true when the record has a photo. |
registryState | The state whose registry lists the person. |
These fields are enough for a popup. They cost nothing beyond the map request that returned them.
Many-people pin
Several people at one address are one pin. It has id: null, a count and a groupId.
| Field | Meaning |
|---|---|
id | Always null. There is no single record behind this pin. |
count | People at the address. |
groupId | The group id, mg_…. Pass it to the groups route. |
members | The people, inline, when there are 10 or fewer and the zoom is 15 or closer. Otherwise use the groups route. |
Approximate-area pin
Some people are known only to the middle of a ZIP, a city or a county. People in custody and people without a fixed address are here too. They come back in areas, never in markers, so they are never drawn as an exact pin.
| Field | Meaning |
|---|---|
lat, lng | The middle of the area. |
count | People in it. |
precision | zip, city or county. |
label | The name of the area, such as a ZIP code. |
groupId | Pass it to the groups route for the people. |
Draw an area pin so it does not look like an address: a dashed circle, a different colour, and the word “approximate”.
The groups route
GET /v1/map/groups/{groupId} lists the people behind a many-people pin or an approximate-area pin. Each page is one map request.
curl "https://api.offendersearch.app/v1/map/groups/mg_8Uo…?page=1&perPage=50" \
-H "X-API-Key: $OFFENDERSEARCH_KEY"{
"total": 12,
"page": 1,
"perPage": 50,
"totalPages": 1,
"kind": "address",
"named": true,
"members": [
{
"id": "mk_…",
"addressType": "home",
"label": "Sample S. Demo",
"housingStatus": null,
"hasPhoto": false
}
],
"notice": "A pin shows a registered address, not a person's current location."
}| Field | Meaning |
|---|---|
page, perPage | Query parameters. page starts at 1. perPage is 1 to 100; the default is 50. |
total, totalPages | People in the group, and pages at this perPage. |
kind | address for a many-people pin, area for an approximate-area pin. |
named | true when the group id came from a view at zoom 15 or closer. Members carry label only then. |
members[].id | A marker id. Pass it to the records route. |
The breakdown
breakdown is on the view and on every cluster. Its four numbers are not a split of the total: one person can count in two of them.
| Field | Counts |
|---|---|
street | People with an exact street address. |
housed | People the registry lists as housed. |
homeless | People the registry lists as homeless. |
incarcerated | People the registry lists as in custody. |
People whose registry does not state a housing status are in total and in none of the three housing numbers.
Unplaced people
unplaced counts people in the states the view touches who have no mappable address. They are on a registry, and they are not on the map.
"unplaced": {"count": 96, "states": ["OH"]}Say so next to the map, so a short list of pins is not read as the whole list. For example: “96 more people are registered in Ohio with no mappable address. Search by name to find them.” The count is for whole states, not for the box.
GeoJSON
With format=geojson the answer is a FeatureCollection of points, with content type application/geo+json. It can go straight into a map library’s GeoJSON source.
{
"type": "FeatureCollection",
"features": [
{
"type": "Feature",
"geometry": {"type": "Point", "coordinates": [-82.9988, 39.9612]},
"properties": {
"cluster": true,
"cluster_id": "c10_1103_1551",
"point_count": 412,
"point_count_abbreviated": "412",
"expansion_zoom": 11,
"bbox": [-83.06, 39.91, -82.97, 39.98],
"breakdown_street": 412,
"breakdown_housed": 201,
"breakdown_homeless": 77,
"breakdown_incarcerated": 0
}
}
],
"meta": {"mode": "clusters", "zoom": 10, "total": 508}
}| Feature | Properties |
|---|---|
| Cluster | cluster: true, cluster_id, point_count, point_count_abbreviated, expansion_zoom, bbox, and breakdown_street, breakdown_housed, breakdown_homeless, breakdown_incarcerated. |
| Pin | The pin’s fields, plus kind: "marker". |
| Many-people pin | The pin’s fields, plus kind: "group". |
| Approximate area | The area’s fields, plus kind: "area". |
Everything that is not a feature, such as mode, zoom, total, unplaced and notice, is under meta. For a heat map, use the cluster features with point_count as the weight.