geojson

package
v0.4.2 Latest Latest
Warning

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

Go to latest
Published: Feb 24, 2022 License: MIT Imports: 4 Imported by: 0

README

orb/geojson Godoc Reference

This package encodes and decodes GeoJSON into Go structs using the geometries in the orb package. Supports both the json.Marshaler and json.Unmarshaler interfaces. The package also provides helper functions such as UnmarshalFeatureCollection and UnmarshalFeature.

Unmarshalling (JSON -> Go)

rawJSON := []byte(`
  { "type": "FeatureCollection",
    "features": [
      { "type": "Feature",
        "geometry": {"type": "Point", "coordinates": [102.0, 0.5]},
        "properties": {"prop0": "value0"}
      }
    ]
  }`)

fc, _ := geojson.UnmarshalFeatureCollection(rawJSON)

// or

fc := geojson.NewFeatureCollection()
err := json.Unmarshal(rawJSON, &fc)

// Geometry will be unmarshalled into the correct geo.Geometry type.
point := fc.Features[0].Geometry.(orb.Point)

Marshalling (Go -> JSON)

fc := geojson.NewFeatureCollection()
fc.Append(geojson.NewFeature(orb.Point{1, 2}))

rawJSON, _ := fc.MarshalJSON()

// or
blob, _ := json.Marshal(fc)

Foreign/extra members in a feature collection

rawJSON := []byte(`
  { "type": "FeatureCollection",
    "generator": "myapp",
    "timestamp": "2020-06-15T01:02:03Z",
    "features": [
      { "type": "Feature",
        "geometry": {"type": "Point", "coordinates": [102.0, 0.5]},
        "properties": {"prop0": "value0"}
      }
    ]
  }`)

fc, _ := geojson.UnmarshalFeatureCollection(rawJSON)

fc.ExtraMembers["generator"] // == "myApp"
fc.ExtraMembers["timestamp"] // == "2020-06-15T01:02:03Z"

// Marshalling will include values in `ExtraMembers` in the
// base featureCollection object.

Feature Properties

GeoJSON features can have properties of any type. This can cause issues in a statically typed language such as Go. Included is a Properties type with some helper methods that will try to force convert a property. An optional default, will be used if the property is missing or the wrong type.

f.Properties.MustBool(key string, def ...bool) bool
f.Properties.MustFloat64(key string, def ...float64) float64
f.Properties.MustInt(key string, def ...int) int
f.Properties.MustString(key string, def ...string) string

Documentation

Overview

Package geojson is a library for encoding and decoding GeoJSON into Go structs using the geometries in the orb package. Supports both the json.Marshaler and json.Unmarshaler interfaces as well as helper functions such as `UnmarshalFeatureCollection` and `UnmarshalFeature`.

Example (Unmarshal)
package main

import (
	"encoding/json"
	"fmt"
	"log"

	"github.com/dadadamarine/orb"
	"github.com/dadadamarine/orb/geojson"
)

func main() {
	rawJSON := []byte(`
	  { "type": "FeatureCollection",
	    "features": [
	      { "type": "Feature",
	        "geometry": {"type": "Point", "coordinates": [102.0, 0.5]},
	        "properties": {"prop0": "value0"}
	      }
	    ]
	  }`)

	fc := geojson.NewFeatureCollection()
	err := json.Unmarshal(rawJSON, &fc)
	if err != nil {
		log.Fatalf("invalid json: %v", err)
	}

	// Geometry will be unmarshalled into the correct geo.Geometry type.
	point := fc.Features[0].Geometry.(orb.Point)
	fmt.Println(point)

}
Output:

[102 0.5]

Index

Examples

Constants

View Source
const (
	TypePoint           = "Point"
	TypeMultiPoint      = "MultiPoint"
	TypeLineString      = "LineString"
	TypeMultiLineString = "MultiLineString"
	TypePolygon         = "Polygon"
	TypeMultiPolygon    = "MultiPolygon"
)

A list of the geojson types that are currently supported.

Variables

View Source
var ErrInvalidGeometry = errors.New("geojson: invalid geometry")

ErrInvalidGeometry will be returned if a the json of the geometry is invalid.

Functions

This section is empty.

Types

type BBox

type BBox []float64

BBox is for the geojson bbox attribute which is an array with all axes of the most southwesterly point followed by all axes of the more northeasterly point.

func NewBBox

func NewBBox(b orb.Bound) BBox

NewBBox creates a bbox from a a bound.

func (BBox) Bound

func (bb BBox) Bound() orb.Bound

Bound returns the orb.Bound for the BBox.

func (BBox) Valid

func (bb BBox) Valid() bool

Valid checks if the bbox is present and has at least 4 elements.

type Feature

type Feature struct {
	ID         interface{}  `json:"id,omitempty"`
	Type       string       `json:"type"`
	BBox       BBox         `json:"bbox,omitempty"`
	Geometry   orb.Geometry `json:"geometry"`
	Properties Properties   `json:"properties"`
}

A Feature corresponds to GeoJSON feature object

func NewFeature

func NewFeature(geometry orb.Geometry) *Feature

NewFeature creates and initializes a GeoJSON feature given the required attributes.

func UnmarshalFeature

func UnmarshalFeature(data []byte) (*Feature, error)

UnmarshalFeature decodes the data into a GeoJSON feature. Alternately one can call json.Unmarshal(f) directly for the same result.

func (Feature) MarshalJSON

func (f Feature) MarshalJSON() ([]byte, error)

MarshalJSON converts the feature object into the proper JSON. It will handle the encoding of all the child geometries. Alternately one can call json.Marshal(f) directly for the same result.

func (*Feature) Point

func (f *Feature) Point() orb.Point

Point implements the orb.Pointer interface so that Features can be used with quadtrees. The point returned is the center of the Bound of the geometry. To represent the geometry with another point you must create a wrapper type.

Example
package main

import (
	"fmt"

	"github.com/dadadamarine/orb"
	"github.com/dadadamarine/orb/geojson"
	"github.com/dadadamarine/orb/quadtree"
)

func main() {
	f := geojson.NewFeature(orb.Point{1, 1})
	f.Properties["key"] = "value"

	qt := quadtree.New(f.Geometry.Bound().Pad(1))
	qt.Add(f) // add the feature to a quadtree

	// type assert the feature back into a Feature from
	// the orb.Pointer interface.
	feature := qt.Find(orb.Point{0, 0}).(*geojson.Feature)
	fmt.Printf("key=%s", feature.Properties["key"])

}
Output:

key=value

func (*Feature) UnmarshalJSON

func (f *Feature) UnmarshalJSON(data []byte) error

UnmarshalJSON handles the correct unmarshalling of the data into the orb.Geometry types.

type FeatureCollection

type FeatureCollection struct {
	Type     string     `json:"type"`
	BBox     BBox       `json:"bbox,omitempty"`
	Features []*Feature `json:"features"`

	// ExtraMembers can be used to encoded/decode extra key/members in
	// the base of the feature collection. Note that keys of "type", "bbox"
	// and "features" will not work as those are reserved by the GeoJSON spec.
	ExtraMembers Properties `json:"-"`
}

A FeatureCollection correlates to a GeoJSON feature collection.

Example (ForeignMembers)
package main

import (
	"encoding/json"
	"fmt"

	"github.com/dadadamarine/orb/geojson"
)

func main() {
	rawJSON := []byte(`
	  { "type": "FeatureCollection",
	    "features": [
	      { "type": "Feature",
	        "geometry": {"type": "Point", "coordinates": [102.0, 0.5]},
	        "properties": {"prop0": "value0"}
	      }
	    ],
	    "title": "Title as Foreign Member"
	  }`)

	fc := geojson.NewFeatureCollection()
	json.Unmarshal(rawJSON, &fc)

	fmt.Println(fc.Features[0].Geometry)
	fmt.Println(fc.ExtraMembers["title"])

	data, _ := json.Marshal(fc)
	fmt.Println(string(data))

}
Output:

[102 0.5]
Title as Foreign Member
{"features":[{"type":"Feature","geometry":{"type":"Point","coordinates":[102,0.5]},"properties":{"prop0":"value0"}}],"title":"Title as Foreign Member","type":"FeatureCollection"}
Example (ForeignMembersCustom)
package main

import (
	"encoding/json"
	"fmt"

	"github.com/dadadamarine/orb/geojson"
)

// MyFeatureCollection is a depricated/no longer supported way to extract
// foreign/extra members from a feature collection. Now an UnmarshalJSON
// method, like below, is required for it to work.
type MyFeatureCollection struct {
	geojson.FeatureCollection
	Title string `json:"title"`
}

// UnmarshalJSON implemented as below is now required for the extra members
// to be decoded directly into the type.
func (fc *MyFeatureCollection) UnmarshalJSON(data []byte) error {
	err := json.Unmarshal(data, &fc.FeatureCollection)
	if err != nil {
		return err
	}

	fc.Title = fc.ExtraMembers.MustString("title", "")
	return nil
}

func main() {
	// Note: this approach to handling foreign/extra members requires
	// implementing an `UnmarshalJSON` method on the new type.
	// See MyFeatureCollection type and its UnmarshalJSON function above.

	rawJSON := []byte(`
	  { "type": "FeatureCollection",
	    "features": [
	      { "type": "Feature",
	        "geometry": {"type": "Point", "coordinates": [102.0, 0.5]},
	        "properties": {"prop0": "value0"}
	      }
	    ],
	    "title": "Title as Foreign Member"
	  }`)

	fc := &MyFeatureCollection{}
	json.Unmarshal(rawJSON, &fc)

	fmt.Println(fc.FeatureCollection.Features[0].Geometry)
	fmt.Println(fc.Features[0].Geometry)
	fmt.Println(fc.Title)
}
Output:

[102 0.5]
[102 0.5]
Title as Foreign Member

func NewFeatureCollection

func NewFeatureCollection() *FeatureCollection

NewFeatureCollection creates and initializes a new feature collection.

func UnmarshalFeatureCollection

func UnmarshalFeatureCollection(data []byte) (*FeatureCollection, error)

UnmarshalFeatureCollection decodes the data into a GeoJSON feature collection. Alternately one can call json.Unmarshal(fc) directly for the same result.

Example
package main

import (
	"fmt"

	"github.com/dadadamarine/orb"
	"github.com/dadadamarine/orb/geojson"
)

func main() {
	rawJSON := []byte(`
	  { "type": "FeatureCollection",
	    "features": [
	      { "type": "Feature",
	        "geometry": {"type": "Point", "coordinates": [102.0, 0.5]},
	        "properties": {"prop0": "value0"}
	      }
	    ]
	  }`)

	fc, _ := geojson.UnmarshalFeatureCollection(rawJSON)

	// Geometry will be unmarshalled into the correct geo.Geometry type.
	point := fc.Features[0].Geometry.(orb.Point)
	fmt.Println(point)

}
Output:

[102 0.5]

func (*FeatureCollection) Append

func (fc *FeatureCollection) Append(feature *Feature) *FeatureCollection

Append appends a feature to the collection.

func (FeatureCollection) MarshalJSON

func (fc FeatureCollection) MarshalJSON() ([]byte, error)

MarshalJSON converts the feature collection object into the proper JSON. It will handle the encoding of all the child features and geometries. Alternately one can call json.Marshal(fc) directly for the same result. Items in the ExtraMembers map will be included in the base of the feature collection object.

Example
package main

import (
	"encoding/json"
	"fmt"
	"log"

	"github.com/dadadamarine/orb"
	"github.com/dadadamarine/orb/geojson"
)

func main() {
	fc := geojson.NewFeatureCollection()
	fc.Append(geojson.NewFeature(orb.Point{1, 2}))

	data, err := fc.MarshalJSON()
	if err != nil {
		log.Fatalf("marshal error: %v", err)
	}

	// standard lib encoding/json package will also work
	data, err = json.MarshalIndent(fc, "", " ")
	if err != nil {
		log.Fatalf("marshal error: %v", err)
	}

	fmt.Println(string(data))

}
Output:

{
 "features": [
  {
   "type": "Feature",
   "geometry": {
    "type": "Point",
    "coordinates": [
     1,
     2
    ]
   },
   "properties": null
  }
 ],
 "type": "FeatureCollection"
}

func (*FeatureCollection) UnmarshalJSON added in v0.4.1

func (fc *FeatureCollection) UnmarshalJSON(data []byte) error

UnmarshalJSON decodes the data into a GeoJSON feature collection. Extra/foreign members will be put into the `ExtraMembers` attribute.

type Geometry

type Geometry struct {
	Type        string       `json:"type"`
	Coordinates orb.Geometry `json:"coordinates,omitempty"`
	Geometries  []*Geometry  `json:"geometries,omitempty"`
}

A Geometry matches the structure of a GeoJSON Geometry.

func NewGeometry

func NewGeometry(g orb.Geometry) *Geometry

NewGeometry will create a Geometry object but will convert the input into a GoeJSON geometry. For example, it will convert Rings and Bounds into Polygons.

func UnmarshalGeometry

func UnmarshalGeometry(data []byte) (*Geometry, error)

UnmarshalGeometry decodes the data into a GeoJSON feature. Alternately one can call json.Unmarshal(g) directly for the same result.

func (Geometry) Geometry

func (g Geometry) Geometry() orb.Geometry

Geometry returns the orb.Geometry for the geojson Geometry. This will convert the "Geometries" into a orb.Collection if applicable.

func (Geometry) MarshalJSON

func (g Geometry) MarshalJSON() ([]byte, error)

MarshalJSON will marshal the geometry into the correct json structure.

func (*Geometry) UnmarshalJSON

func (g *Geometry) UnmarshalJSON(data []byte) error

UnmarshalJSON will unmarshal the correct geometry from the json structure.

type LineString

type LineString orb.LineString

A LineString is a helper type that will marshal to/from a GeoJSON LineString geometry.

func (LineString) Geometry

func (ls LineString) Geometry() orb.Geometry

Geometry will return the orb.Geometry version of the data.

func (LineString) MarshalJSON

func (ls LineString) MarshalJSON() ([]byte, error)

MarshalJSON will convert the LineString into a GeoJSON LineString geometry.

func (*LineString) UnmarshalJSON

func (ls *LineString) UnmarshalJSON(data []byte) error

UnmarshalJSON will unmarshal the GeoJSON MultiPoint geometry.

type MultiLineString

type MultiLineString orb.MultiLineString

A MultiLineString is a helper type that will marshal to/from a GeoJSON MultiLineString geometry.

func (MultiLineString) Geometry

func (mls MultiLineString) Geometry() orb.Geometry

Geometry will return the orb.Geometry version of the data.

func (MultiLineString) MarshalJSON

func (mls MultiLineString) MarshalJSON() ([]byte, error)

MarshalJSON will convert the MultiLineString into a GeoJSON MultiLineString geometry.

func (*MultiLineString) UnmarshalJSON

func (mls *MultiLineString) UnmarshalJSON(data []byte) error

UnmarshalJSON will unmarshal the GeoJSON MultiPoint geometry.

type MultiPoint

type MultiPoint orb.MultiPoint

A MultiPoint is a helper type that will marshal to/from a GeoJSON MultiPoint geometry.

func (MultiPoint) Geometry

func (mp MultiPoint) Geometry() orb.Geometry

Geometry will return the orb.Geometry version of the data.

func (MultiPoint) MarshalJSON

func (mp MultiPoint) MarshalJSON() ([]byte, error)

MarshalJSON will convert the MultiPoint into a GeoJSON MultiPoint geometry.

func (*MultiPoint) UnmarshalJSON

func (mp *MultiPoint) UnmarshalJSON(data []byte) error

UnmarshalJSON will unmarshal the GeoJSON MultiPoint geometry.

type MultiPolygon

type MultiPolygon orb.MultiPolygon

A MultiPolygon is a helper type that will marshal to/from a GeoJSON MultiPolygon geometry.

func (MultiPolygon) Geometry

func (mp MultiPolygon) Geometry() orb.Geometry

Geometry will return the orb.Geometry version of the data.

func (MultiPolygon) MarshalJSON

func (mp MultiPolygon) MarshalJSON() ([]byte, error)

MarshalJSON will convert the MultiPolygon into a GeoJSON MultiPolygon geometry.

func (*MultiPolygon) UnmarshalJSON

func (mp *MultiPolygon) UnmarshalJSON(data []byte) error

UnmarshalJSON will unmarshal the GeoJSON MultiPolygon geometry.

type Point

type Point orb.Point

A Point is a helper type that will marshal to/from a GeoJSON Point geometry.

func (Point) Geometry

func (p Point) Geometry() orb.Geometry

Geometry will return the orb.Geometry version of the data.

func (Point) MarshalJSON

func (p Point) MarshalJSON() ([]byte, error)

MarshalJSON will convert the Point into a GeoJSON Point geometry.

func (*Point) UnmarshalJSON

func (p *Point) UnmarshalJSON(data []byte) error

UnmarshalJSON will unmarshal the GeoJSON Point geometry.

type Polygon

type Polygon orb.Polygon

A Polygon is a helper type that will marshal to/from a GeoJSON Polygon geometry.

func (Polygon) Geometry

func (p Polygon) Geometry() orb.Geometry

Geometry will return the orb.Geometry version of the data.

func (Polygon) MarshalJSON

func (p Polygon) MarshalJSON() ([]byte, error)

MarshalJSON will convert the Polygon into a GeoJSON Polygon geometry.

func (*Polygon) UnmarshalJSON

func (p *Polygon) UnmarshalJSON(data []byte) error

UnmarshalJSON will unmarshal the GeoJSON Polygon geometry.

type Properties

type Properties map[string]interface{}

Properties defines the feature properties with some helper methods.

func (Properties) Clone

func (p Properties) Clone() Properties

Clone returns a shallow copy of the properties.

func (Properties) MustBool

func (p Properties) MustBool(key string, def ...bool) bool

MustBool guarantees the return of a `bool` (with optional default). This function useful when you explicitly want a `bool` in a single value return context, for example:

myFunc(f.Properties.MustBool("param1"), f.Properties.MustBool("optional_param", true))

This function will panic if the value is present but not a bool.

func (Properties) MustFloat64

func (p Properties) MustFloat64(key string, def ...float64) float64

MustFloat64 guarantees the return of a `float64` (with optional default) This function useful when you explicitly want a `float64` in a single value return context, for example:

myFunc(f.Properties.MustFloat64("param1"), f.Properties.MustFloat64("optional_param", 10.1))

This function will panic if the value is present but not a number.

func (Properties) MustInt

func (p Properties) MustInt(key string, def ...int) int

MustInt guarantees the return of an `int` (with optional default). This function useful when you explicitly want a `int` in a single value return context, for example:

myFunc(f.Properties.MustInt("param1"), f.Properties.MustInt("optional_param", 123))

This function will panic if the value is present but not a number.

func (Properties) MustString

func (p Properties) MustString(key string, def ...string) string

MustString guarantees the return of a `string` (with optional default) This function useful when you explicitly want a `string` in a single value return context, for example:

myFunc(f.Properties.MustString("param1"), f.Properties.MustString("optional_param", "default"))

This function will panic if the value is present but not a string.

Jump to

Keyboard shortcuts

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