Add API to query district by GPS location

This commit is contained in:
Eli Ribble 2026-01-15 22:56:32 +00:00
parent 0bb055b391
commit f6b5a1e580
No known key found for this signature in database
5 changed files with 86 additions and 0 deletions

View file

@ -78,6 +78,39 @@ func apiAudioContentPost(w http.ResponseWriter, r *http.Request, u *models.User)
w.WriteHeader(http.StatusOK)
}
func apiGetDistrict(w http.ResponseWriter, r *http.Request) {
var latStr, lngStr string
err := r.ParseForm()
if err != nil {
render.Render(w, r, errRender(fmt.Errorf("Failed to parse GET form: %w", err)))
return
} else {
latStr = r.FormValue("lat")
lngStr = r.FormValue("lng")
}
lat, err := strconv.ParseFloat(latStr, 64)
if err != nil {
render.Render(w, r, errRender(fmt.Errorf("Failed to parse lat as float: %w", err)))
return
}
lng, err := strconv.ParseFloat(lngStr, 64)
if err != nil {
render.Render(w, r, errRender(fmt.Errorf("Failed to parse lng as float: %w", err)))
return
}
district, err := platform.DistrictForLocation(r.Context(), lng, lat)
if err != nil {
render.Render(w, r, errRender(fmt.Errorf("Failed to get district: %w", err)))
return
}
d := ResponseDistrict{
Agency: district.Agency.GetOr(""),
}
if err := render.Render(w, r, d); err != nil {
render.Render(w, r, errRender(err))
}
}
func handleClientIos(w http.ResponseWriter, r *http.Request, u *models.User) {
var sinceStr string
err := r.ParseForm()

View file

@ -20,6 +20,7 @@ func AddRoutes(r chi.Router) {
r.Method("POST", "/image/{uuid}/content", auth.NewEnsureAuth(apiImageContentPost))
// Unauthenticated endpoints
r.Get("/district", apiGetDistrict)
r.Get("/webhook/fieldseeker", webhookFieldseeker)
r.Post("/webhook/fieldseeker", webhookFieldseeker)
}

View file

@ -62,6 +62,10 @@ type NoteAudioPayload struct {
Version int32 `json:"version"`
}
type ResponseDistrict struct {
Agency string `json:"agency"`
}
type ResponseMosquitoSource struct {
Access string `json:"access"`
Active *bool `json:"active"`
@ -154,6 +158,10 @@ func NewResponseMosquitoInspections(inspections models.FieldseekerMosquitoinspec
return results
}
func (rd ResponseDistrict) Render(w http.ResponseWriter, r *http.Request) error {
return nil
}
func (rtd ResponseMosquitoSource) Render(w http.ResponseWriter, r *http.Request) error {
return nil
}

31
platform/district.go Normal file
View file

@ -0,0 +1,31 @@
package platform
import (
"context"
"fmt"
"github.com/Gleipnir-Technology/nidus-sync/db"
"github.com/Gleipnir-Technology/nidus-sync/db/models"
"github.com/stephenafamo/bob/dialect/psql"
"github.com/stephenafamo/bob/dialect/psql/sm"
)
func DistrictForLocation(ctx context.Context, lng float64, lat float64) (*models.District, error) {
rows, err := models.Districts.Query(
sm.Where(
psql.F("ST_Contains", psql.Raw("geom_4326"), psql.F("ST_SetSRID", psql.F("ST_MakePoint", psql.Arg(lng), psql.Arg(lat)), psql.Arg(4326))),
),
).All(ctx, db.PGInstance.BobDB)
if err != nil {
return nil, fmt.Errorf("failed to query district: %w", err)
}
switch len(rows) {
case 0:
return nil, nil
case 1:
return rows[0], nil
default:
return nil, nil
}
}

View file

@ -35,6 +35,18 @@ function setDistrictColors(map) {
//console.log("using fallback district coloring");
}
}
async function fetchDistrict(lng, lat) {
try {
const url = `/api/district?lat=${lat}&lng=${lng}`
const response = await fetch(url);
const data = await response.json();
console.log("district", data);
} catch (error) {
console.error('Error fetching geocoding suggestions:', error);
}
}
function onLoad() {
console.log("Setting up the map...");
mapboxgl.accessToken = MAPBOX_ACCESS_TOKEN;
@ -118,6 +130,7 @@ function onLoad() {
});*/
addressDisplay.show(l);
fetchDistrict(l.geometry.coordinates[0], l.geometry.coordinates[1]);
});
}
document.addEventListener("DOMContentLoaded", onLoad);