src

command
v4.1.0+incompatible Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 16, 2020 License: Apache-2.0 Imports: 22 Imported by: 0

Documentation

Overview

Horizon GPS Data REST API

This REST server enables workload access to static location or dynamic GPS receiver location and satellite data.

Currently the data available through this API includes only:

  • the surface location (latitude and longitude) of the node using the "decimal coordinates" system. GPS decimal coordinates have the following properties:
  • latitudes are always in the range between -90.0 deg to 90.0 deg, where:
  • latitudes between 0 deg and 90 deg are Northern hemisphere, and
  • latitudes between 0 deg and -90 deg are Southern hemisphere.
  • longitudes are always in the range between -180.0 deg to 180.0 deg, where:
  • longitudes between 0 deg and 180 deg are East of Greenwich meridian, and
  • longitudes between 0 deg and -180 deg are West of Greenwich meridian.
  • the vertical location (elevation, or altitude) of the node relative to global sea level. When not provided, this is computed using the USGS public elevation query REST API.
  • location accuracy information. This is always 0 when GPS hardware is being used (GPS data is never obfuscated by this code) or when the location is estimated using the public IP address of the node. When location obfuscation of a static location is requested, the accuracy must be specified in kilometers. Note that location obfuscation is always computed only once, creating a new and persistent (obfuscated) static location for the node. As a result the gps REST API cannot be used repeatedly in concert with a Monte Carlo technique to derive a more precise location defeating the obfuscation.
  • the source of the location data (i.e., from "GPS", or a specified "Manual" location, or an "Estimated" location derived from the public IP address of the node). Note that when GPS hardware is being used, and a GPS *fix* has not been achieved, the source will be given as "Searching". If previously aquired location data is available, that old data is provided while searching for a "fix".

* data about the discovered satellites (only if using GPS, of course)

Notice that the location of the node as provided by this API may be dynamic (provided by GPS hardware), or it may be static. It may be relatively precise (when dynamic with a "fix", or when precisely provided statically), or it may be approximate (derived from the public IP address of the node, or deliberately obfuscated within a specified distance from a statically provided location), or it may be completely fictional (which is useful for testing and other purposes).

The various different ways that this service operates are controlled by runtime configuration provided by variables in the process environment. For example, this microservice could be started as follows:

$ env HZN_GPS_PORT=12345 \
      HZN_USE_GPS=false \
      HZN_LAT=37.0 \
      HZN_LON=-121.0 \
      HZN_LOCATION_ACCURACY_KM=10.0 \
      go run ...

The example above configures manually specified (lat/lon) coordinates and disables the use of any GPS hardware that might be present. It also configures location obfuscation and sets the location accuracy within 10km of the statically provided location.

Given the above server configuration, a typical request/response interaction with the service should be similar to what is shown below:

$ curl -s ...:12345/v1/gps | jq
{
  "location": {
    "latitude": 36.973370118640865,
    "longitude": -121.00122383303518,
    "elevation": 183.69,
    "accuracy_km": 10,
    "loc_source": "Estimated",
    "loc_last_update": 1486401329
  },
  "satellites": null
}
$

If you have the appropriate GPS hardware atached you could instead run the server as follows to enable the gps microservice to use it:

$ env HZN_GPS_PORT=12345 \
      HZN_USE_GPS=true
      go run ...

Note that the environment variables HZN_LON, HZN_LAT, HZN_LOCATION_ACCURACY are ignored when HZN_USE_GPS is set, so these variables are not being set in this example.

Since the above configuration tells the server that GPS hardware is available, the expected response would typically be similar to that shown below (assuming the GPS hardware has acquired a "fix"):

  $ curl -s ...:12345/v1/gps | jq
  {
    "location": {
      "latitude": 37.273474,
      "longitude": -121.880242,
      "elevation": 37.3,
      "accuracy_km": 0,
      "loc_source": "GPS",
      "loc_last_update": 1486416035
    },
    "satellites": [
      {
        "PRN": 1,
        "az": 195,
        "el": 0,
        "ss": 0,
        "used": false
      },
      {
        "PRN": 3,
        "az": 175,
        "el": 56,
        "ss": 18,
        "used": true
      },

... <likely with many more satellites listed>

      {
      {
        "PRN": 23,
        "az": 1,
        "el": 70,
        "ss": 15,
        "used": true
      }
    ]
  }
  $

Written by Glen Darling (glendarling@us.ibm.com), Oct. 2016

Directories

Path Synopsis
envutil -- utilities for getting configuration from environment variables.
envutil -- utilities for getting configuration from environment variables.
gpsdc -- a Go client for the gpsd daemon Usage example: package main import ( "fmt" "gpsdc" ) func main() { var gps_monitor *gpsdc.Session var err error // Open socket to gpsd at specified address (using default here) if gps_monitor, err = gpsdc.Dial(gpsdc.DefaultAddress); err != nil { panic(fmt.Sprintf("Failed to connect to GPSD: ", err)) } // Add an inline Filter function gps_monitor.AddFilter("TPV", func (r interface{}) { report := r.(*gpsdc.TPVReport) fmt.Printf("TPV: Lat=%f, Lon=%f, Alt=%f\n", report.Lat, report.Lon, report.Alt) }) // Or a stand-alone Filter function skyfilter := func(r interface{}) { sky := r.(*gpsdc.SKYReport) fmt.Printf("SKY: %d satellites\n", len(sky.Satellites)) } gps_monitor.AddFilter("SKY", skyfilter) // Tell gpsdc to start watching (using the default watch command here) gps_monitor.SendCommand(gpsdc.DefaultWatchCommand) // Listen forever for reports (delivered to the Filters above) done := gps_monitor.Listen() <- done } This code is Based on the incomplete and apparently abandoned 2013 project: "https://github.com/stratoberry/go-gpsd" The majority of this code was copied directly from that project.
gpsdc -- a Go client for the gpsd daemon Usage example: package main import ( "fmt" "gpsdc" ) func main() { var gps_monitor *gpsdc.Session var err error // Open socket to gpsd at specified address (using default here) if gps_monitor, err = gpsdc.Dial(gpsdc.DefaultAddress); err != nil { panic(fmt.Sprintf("Failed to connect to GPSD: ", err)) } // Add an inline Filter function gps_monitor.AddFilter("TPV", func (r interface{}) { report := r.(*gpsdc.TPVReport) fmt.Printf("TPV: Lat=%f, Lon=%f, Alt=%f\n", report.Lat, report.Lon, report.Alt) }) // Or a stand-alone Filter function skyfilter := func(r interface{}) { sky := r.(*gpsdc.SKYReport) fmt.Printf("SKY: %d satellites\n", len(sky.Satellites)) } gps_monitor.AddFilter("SKY", skyfilter) // Tell gpsdc to start watching (using the default watch command here) gps_monitor.SendCommand(gpsdc.DefaultWatchCommand) // Listen forever for reports (delivered to the Filters above) done := gps_monitor.Listen() <- done } This code is Based on the incomplete and apparently abandoned 2013 project: "https://github.com/stratoberry/go-gpsd" The majority of this code was copied directly from that project.
hgps -- a resource class for caching Horizon GPS data Cache your Horizon GPS data in a "smart" GpsCache instance.
hgps -- a resource class for caching Horizon GPS data Cache your Horizon GPS data in a "smart" GpsCache instance.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL