Aufruffunktion im Abfrage-Generator


8

Ich habe eine Standorteinheit mit Koordinaten. Basierend auf einem Radius möchte ich alle Orte erhalten, die sich in Reichweite befinden.

Ich habe eine Funktion erstellt (Backend-Code / Nestjs-Logik, keine Datenbank), die den Abstand zwischen zwei Standorten berechnet. Wenn der berechnete Abstand kleiner oder gleich dem Radius ist, möchte ich diesen Ort auswählen.

Meine aktuelle Repository-Implementierung mit dieser Entfernungsberechnungsfunktion:

// ...
import { distanceFromCoordinatesInKilometers } from '../shared/calculations/distanceFromCoordinatesInKilometers';

@EntityRepository(Location)
export class LocationsRepository extends Repository<Location> {
    public getLocations({ /* ... */ latitude, longitude, radiusInKilometers }: GetLocationsDTO): Promise<Location[]> {
        const query: SelectQueryBuilder<Location> = this.createQueryBuilder('location');

        // ....

        if(latitude && longitude && radiusInKilometers) {
             query.andWhere("distanceFromCoordinatesInKilometers(location.latitude, location.longitude, :latitude, :longitude) <= :radiusInKilometers", { 
                 latitude,
                 longitude,
                 radiusInKilometers, 
            });
        }

        return query.getMany();
    }
}

Das oben gezeigte Beispiel funktioniert nicht. Ich bekomme diesen Fehler

QueryFailedError: Die Funktion distanceFromCoordinatesInKilometers (doppelte Genauigkeit, doppelte Genauigkeit, unbekannt, unbekannt) ist nicht vorhanden

Beim Hinzufügen von a :zur Funktion wird dieser Fehler angezeigt

Funktionsparameter werden in den Parametern nicht unterstützt. Bitte überprüfen Sie den Parameter "Abstand".

Wie würde ich meine Backend-Code-Funktion aufrufen? distanceFromCoordinatesInKilometers innerhalb dieser Abfrage ? Ich kann Variablen übergeben, aber keine Funktionen?

Derzeit verwende ich eine Postgres-Datenbank, aber es wäre fantastisch, wenn es eine unabhängige Lösung gäbe.


2
Im Grunde versuchen Sie, eine Funktion aus Ihrer node.jsApp aus der Datenbank aufzurufen. Das wird nie funktionieren. Eine universelle Lösung wäre: Implementieren dieser Funktion in der Datenbank (z. B. durch Migrationen) oder eine treiberunabhängigere Lösung: Implementieren dieser Funktion in Ihrer Anfrage
Roomy

Danke, aber wie würde ich diese Funktion in meiner Abfrage implementieren? Die Berechnung selbst ist groß (30 Codezeilen)
Frage

1
Ihre Frage bezieht sich mehr auf SQL als auf TypeORM selbst. Unter der Annahme, dass Sie eine grundlegende Großkreisrechnung verwenden, werfen Sie einen Blick auf das Wesentliche. Gist.github.com/rugbyprof/…
Roomy

Danke für diesen Link. Ich habe versucht, es hier zu übersetzen pastebin.com/AS7y7efr und habe keinen Fehler erhalten. Aber ich muss überprüfen, ob diese Berechnung korrekt ist ...
Frage

1
Haben Sie sich die PostGIS- Erweiterung für PostgreSQL angesehen? Es enthält Funktionen zum Bestimmen von Abständen zwischen Koordinaten (Punkten). Unter gis.stackexchange.com/questions/77072/… finden Sie einige Beispiele, wie Sie eine Abfrage filtern können, die Zeilen in einem bestimmten Abstand von einer angegebenen Koordinate filtert .
Timshel

Antworten:


0

OK Wenn Sie Folgendes in Ihren Code implementieren möchten, müssen Sie die Funktion auswerten, bevor Sie sie an die SQL-Zeichenfolge übergeben. Also einfach:

if(latitude && longitude && radiusInKilometers) {
             query.andWhere(`${distanceFromCoordinatesInKilometers(location.latitude, location.longitude, :latitude, :longitude)} <= :radiusInKilometers`, { 
                 latitude,
                 longitude,
                 radiusInKilometers, 
            });
        }

Entschuldigung, ich habe Ihre Antwort nicht verstanden. Dies ist ein NestJs-Projekt (Node with TS) mit TypeORM. Was soll ich in meinem Code tun?
Frage

@ Question3r C edit
bluejayke

Entschuldigung, aber das funktioniert nicht, da die Funktion die aktuellen Latlong-Werte aus der Datenbanktabelle hier nicht kenntlocation.latitude, location.longitude
Frage
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.