Geofield-Daten programmgesteuert aktualisieren

9

Mein Setup ist:

  1. Adressfeld auf Knoten zum Sammeln von Adressdaten
  2. Geofield verwendet "Geocode aus einem anderen Feld" und wählt das Adressfeld und den Google Geocoder aus

Wenn ich einen Knoten in der Benutzeroberfläche bearbeite / speichere, werden die Daten geokodiert. Ich habe jedoch Tausende von Knoten und versuche, ein Skript zu schreiben, um die Geocode-Informationen auf jedem Knoten zu aktualisieren.

Ich habe versucht, alle Knoten zu laden und ein node_save () auszuführen, aber die Geocode-Hooks wurden nicht ausgelöst.

Wie kann ich die Geofeldinformationen programmgesteuert aktualisieren? Gibt es einen Haken, den ich benutzen kann?

Feature
quelle

Antworten:

4

Laut README.TXT:

API-HINWEISE

Geofield-Felder enthalten neun Informationsspalten zu den gespeicherten geografischen Daten. Das Herzstück ist die Spalte "wkt", in der die vollständige Geometrie im WKT-Format (Well Known Text) gespeichert wird. Alle anderen Spalten sind Metadaten, die von der WKT-Spalte abgeleitet sind. Die Spalten lauten wie folgt:

'geom' Rohwert. Standardmäßig als WKB gespeichert, geladen als WKT
'geo_type' Geometrietyp (Punkt, Linienstreifen, Polygon usw.)
'lat' Schwerpunkt (Breite oder Y)
'lon' Schwerpunkt (Länge oder X)
'oben' Begrenzungsrahmen oben ( Breitengrad oder Max Y) 'unten' Begrenzungsrahmen Unten (Breitengrad oder Min Y)
'links' Begrenzungsrahmen links (Längengrad oder Min X)
'rechts' Begrenzungsrahmen rechts (Längengrad oder
max. X) 'Geohash' Geohash-Äquivalent des Geom-Spaltenwerts

Wenn ein Geofeld mit den bereitgestellten Widgets gespeichert wird, werden diese Werte über die Funktion geofield_compute_values ​​übergeben, um abhängige Werte zu berechnen. Standardmäßig werden abhängige Werte basierend auf WKT berechnet. Dies kann jedoch überschrieben werden, um Werte basierend auf anderen Spalten zu berechnen. Zum Beispiel können geofield_compute_values ​​wie folgt aufgerufen werden:

geofield_compute_values ​​($ values, 'latlon');

Dadurch wird das wkt-Feld (und alle anderen Felder) basierend auf den lat / lon-Spalten berechnet, was zu einem Punkt führt. Als Entwickler ist dies wichtig, wenn Sie Geofield-Informationen mit node_load und node_save ändern. Stellen Sie sicher, dass alle geänderten Geofield-Instanzen über geofield_compute_values ​​ausgeführt werden, um alle Spalten konsistent zu machen.

Dies bedeutet:

      $spot->field_coordinates[LANGUAGE_NONE][0] = geofield_compute_values(
          array(
              'lat' => $venue->location->lat, 
              'lon' => $venue->location->lng,
      ), GEOFIELD_INPUT_LAT_LON);
duru
quelle
2

Mit solchen Werten konnte ich die Daten eines Geofelds programmgesteuert aktualisieren :

PHP

$lat = 42.281646;
$lon = -83.744222;
$geofield = array(
  'geom' => "POINT ($lon $lat)",
  'geo_type' => 'point',
  'lat' => $lat . "000000",
  'lon' => $lon . "000000",
  'left' => $lon . "000000",
  'top' => $lat . "000000",
  'right' => $lon . "000000",
  'bottom' => $lat . "000000"
);
$lang = $node->language;
$node->field_position[$lang][0] = $geofield;

JSON for Services-Modul

{
  "nid":123,
  "field_position":{"und":[
    {"geom":{"lat":"42.2808256","lon":"-83.7430378"}}
  ]}
}

In beiden Fällen ist das Widget für das Geofeld Latitude / Longitude, sodass die Ergebnisse für andere Widgets variieren können, insbesondere für das Services- Modul.

tyler.frankenstein
quelle
Aktualisiert dies das geohash?
Beroe
Ich weiß nicht, was du meinst geohash, bitte bestätige, danke.
tyler.frankenstein
Hallo. Entschuldigung für den kryptischen Kommentar. Drupal node__field_geo_fieldhat geohashals letztes Feld ein (siehe API in der obigen Antwort). Das ist eine ASCII-Darstellung einer geografischen Region . Ich weiß nicht, ob sie obligatorisch oder optional sind, aber ich wollte ein Python-Programm erstellen, um sie zu generieren und (zusammen mit lat / long) in die Backend-Drupal-Datenbank einzufügen.
Beroe
Danke für die Bestätigung. Ich selbst bin mit dem geohashWert nicht vertraut , aber vielleicht können Sie die geofield_compute_valuesin der obigen Antwort erwähnte Funktion verwenden, um diesen Wert aus dem lat / lng zu erhalten.
tyler.frankenstein
1

Eine wilde Vermutung: Sie können Ihren Knoten durch den node-edit-formProzess führen, um die Geofeld-Magie abzufeuern.

Schauen Sie sich drupal_form_submit () an , beobachten Sie die $form_state['values']gewöhnliche manuelle Übermittlung des Formulars "Inhalt hinzufügen" Ihres Knotentyps und erstellen Sie es programmgesteuert neu, um es in der drupal_form_submit()Funktion zu senden .

Ich frage mich, ob das funktionieren würde ...

Auf der anderen Seite können Sie einfach die Struktur des Werts Ihres Geofelds überprüfen und diese neu erstellen, indem Sie programmgesteuert die geocoder()Funktion der API des Geocoder- Moduls nutzen.

gue
quelle
0

Sie können die unter https://www.drupal.org/node/905814#comment-4931016 beschriebene Methode verwenden .

  1. Erstellen Sie eine Datenbanksicherung

  2. Machen Sie sich einen Überblick über Ihre Inhalte. Fügen Sie einen Filter hinzu, um den Inhalt auszuwählen, bei dem der geofield-Breitengrad leer ist.

  3. Fügen Sie das Modul Ansichten-Massenoperationen hinzu, fügen Sie ein Feld für Massenoperationen hinzu und wählen Sie als Aktion "Beliebiges PHP ausführen".

    $test = node_load($entity->nid);    
    module_load_include('inc', 'node', 'node.pages');    
    $test_state['values']['op'] = t('Save');    
    drupal_form_submit('NODENAME_node_form', $test_state, $test);

Dieser Ansatz funktioniert einwandfrei, außer dass Datumsfelder, die die Datums-Popup-Anzeige verwenden, leer werden. Seien Sie also vorsichtig, wenn Sie Datumsfelder haben.

Beachten Sie auch, dass der Google-Geocoder ein 24-Stunden-Limit von 2500 Adressen für den Geocode hat.

Hans Rossel
quelle