rgeo-geojson 2.1.1 → 2.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/History.md +6 -0
- data/README.md +1 -1
- data/lib/rgeo/geo_json/coder.rb +1 -4
- data/lib/rgeo/geo_json/collection_methods.rb +35 -0
- data/lib/rgeo/geo_json/conversion_methods.rb +50 -0
- data/lib/rgeo/geo_json/entities.rb +39 -25
- data/lib/rgeo/geo_json/interface.rb +3 -4
- data/lib/rgeo/geo_json/version.rb +1 -1
- data/lib/rgeo/geo_json.rb +6 -5
- data/lib/rgeo-geojson.rb +1 -1
- metadata +11 -9
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 448049463c510bdeb2fa366eaa3834566962116632675ccb509134cc54875fc0
|
4
|
+
data.tar.gz: 7a6c7b327824850c164d3fca314347256e9b8513574afae86687361e92b00c26
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: d6009ac4f8cdd344ca8403235a20d40c71b9dcf891c17a3646650a8b307d863dd5bf2b63d1ce58bcd768f7d394a572f5f14f822ea294818a7c42e307839e0bb6
|
7
|
+
data.tar.gz: 8a53d85316ec32a69a36a287bc6a5f44702427f2b54b9720da82e91fa599aa33e6fd7ccf600f06a1c01442675cf8b267c749506c32151f798c310e4c6060286e
|
data/History.md
CHANGED
data/README.md
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
# rgeo-geojson
|
2
2
|
|
3
3
|
[](http://badge.fury.io/rb/rgeo-geojson)
|
4
|
-
[](https://github.com/rgeo/rgeo-geojson/actions?query=workflow%3ACI+branch%3Amaster+event%3Apush)
|
5
5
|
|
6
6
|
`rgeo-geojson` is an extension to [RGeo](https://github.com/rgeo/rgeo)
|
7
7
|
that provides GeoJSON encoding and decoding.
|
data/lib/rgeo/geo_json/coder.rb
CHANGED
@@ -6,7 +6,6 @@ module RGeo
|
|
6
6
|
# the RGeo::Feature::Factory and the RGeo::GeoJSON::EntityFactory to
|
7
7
|
# be used) so that you can encode and decode without specifying those
|
8
8
|
# settings every time.
|
9
|
-
|
10
9
|
class Coder
|
11
10
|
# Create a new coder settings object. The geo factory is passed as
|
12
11
|
# a required argument.
|
@@ -41,7 +40,6 @@ module RGeo
|
|
41
40
|
# appropriate JSON library installed.
|
42
41
|
#
|
43
42
|
# Returns nil if nil is passed in as the object.
|
44
|
-
|
45
43
|
def encode(object)
|
46
44
|
if @entity_factory.is_feature_collection?(object)
|
47
45
|
{
|
@@ -60,13 +58,12 @@ module RGeo
|
|
60
58
|
# Decode an object from GeoJSON. The input may be a JSON hash, a
|
61
59
|
# String, or an IO object from which to read the JSON string.
|
62
60
|
# If an error occurs, nil is returned.
|
63
|
-
|
64
61
|
def decode(input)
|
65
62
|
if input.is_a?(IO)
|
66
63
|
input = input.read rescue nil
|
67
64
|
end
|
68
65
|
if input.is_a?(String)
|
69
|
-
input =
|
66
|
+
input = MultiJson.load(input)
|
70
67
|
end
|
71
68
|
return unless input.is_a?(Hash)
|
72
69
|
|
@@ -0,0 +1,35 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RGeo
|
4
|
+
# This module is here to fill the gap between what is a GeometryCollection (GIS)
|
5
|
+
# and a FeatureCollection (GeoJSON).
|
6
|
+
#
|
7
|
+
# Note for contributors, you can rely on `@features` to be defined and
|
8
|
+
# you can consider working with an Enumerable wrapping `@features`. See
|
9
|
+
# GeoJSON::FeatureCollection.
|
10
|
+
module GeoJSON::CollectionMethods
|
11
|
+
# There is tight coupling between {FeatureCollection} and this, hence the
|
12
|
+
# guard.
|
13
|
+
private_class_method def self.included(base)
|
14
|
+
return if base.to_s == "RGeo::GeoJSON::FeatureCollection"
|
15
|
+
|
16
|
+
raise Error::RGeoError, "#{self.class} must only be used by FeatureCollection"
|
17
|
+
end
|
18
|
+
|
19
|
+
private def method_missing(symbol, *args)
|
20
|
+
return super unless any? { |feature| feature.respond_to?(symbol) }
|
21
|
+
|
22
|
+
raise Error::UnsupportedOperation, "Method FeatureCollection##{symbol} " \
|
23
|
+
"is not defined. You may consider filing an issue or opening a pull " \
|
24
|
+
"request at https://github.com/rgeo/rgeo-geojson"
|
25
|
+
end
|
26
|
+
|
27
|
+
def contains?(geometry)
|
28
|
+
any? { |feature| feature.contains?(geometry) }
|
29
|
+
end
|
30
|
+
|
31
|
+
def intersects?(geometry)
|
32
|
+
any? { |feature| feature.intersects?(geometry) }
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,50 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module RGeo
|
4
|
+
# This module serves to provide handy methods when using GeoJSON. The methods
|
5
|
+
# provided eases the passage between entities and GeoJSON String/Hash.
|
6
|
+
module GeoJSON::ConversionMethods
|
7
|
+
# Convert a geometry to a GeoJSON Hash
|
8
|
+
def as_geojson
|
9
|
+
GeoJSON.encode(self)
|
10
|
+
end
|
11
|
+
alias as_json as_geojson
|
12
|
+
|
13
|
+
# Convert a geometry to a GeoJSON String
|
14
|
+
def to_geojson
|
15
|
+
::MultiJson.dump(as_geojson)
|
16
|
+
end
|
17
|
+
alias to_json to_geojson
|
18
|
+
end
|
19
|
+
|
20
|
+
# These convenience methods are added directly into the module rather than
|
21
|
+
# including the module above into the Feature::Instance module which is in
|
22
|
+
# every geometry implementation. This is due to a behavior in ruby versions
|
23
|
+
# <3.0.2 where dynamically included modules will not be included automatically
|
24
|
+
# in the ancestor tree.
|
25
|
+
# See https://bugs.ruby-lang.org/issues/9573 for more information.
|
26
|
+
module Feature
|
27
|
+
module Instance
|
28
|
+
# Convert a geometry to a GeoJSON Hash
|
29
|
+
def as_geojson
|
30
|
+
GeoJSON.encode(self)
|
31
|
+
end
|
32
|
+
alias as_json as_geojson
|
33
|
+
|
34
|
+
# Convert a geometry to a GeoJSON String
|
35
|
+
def to_geojson
|
36
|
+
::MultiJson.dump(as_geojson)
|
37
|
+
end
|
38
|
+
alias to_json to_geojson
|
39
|
+
end
|
40
|
+
|
41
|
+
module Factory::Instance
|
42
|
+
# Parses a GeoJSON String/Hash, or an IO object from which
|
43
|
+
# the JSON string is read and returns the corresponding
|
44
|
+
# feature. Returns nil if unable to parse.
|
45
|
+
def parse_geojson(input)
|
46
|
+
GeoJSON.decode(input, geo_factory: self)
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
@@ -1,7 +1,40 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
+
require_relative "collection_methods"
|
4
|
+
require_relative "conversion_methods"
|
5
|
+
|
3
6
|
module RGeo
|
7
|
+
module CastOverlay
|
8
|
+
def self.included(base)
|
9
|
+
# The original {RGeo::Feature.cast} would copy a GeoJSON::Feature, which
|
10
|
+
# fails most operations. When casting, we MUST get a geometry.
|
11
|
+
original_cast = base.method(:cast)
|
12
|
+
base.define_singleton_method(:cast) do |obj, *params|
|
13
|
+
if obj.class == GeoJSON::Feature
|
14
|
+
original_cast.call(obj.geometry, *params)
|
15
|
+
else
|
16
|
+
original_cast.call(obj, *params)
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
Feature.include(CastOverlay)
|
22
|
+
|
4
23
|
module GeoJSON
|
24
|
+
# Simplify usage of inner geometries for Feature and FeatureCollection
|
25
|
+
# objets. Including class must contain a `#geometry` method.
|
26
|
+
module DelegateToGeometry
|
27
|
+
private def method_missing(symbol, *args)
|
28
|
+
return geometry.public_send(symbol, *args) if geometry
|
29
|
+
|
30
|
+
super
|
31
|
+
end
|
32
|
+
|
33
|
+
private def respond_to_missing?(symbol, *)
|
34
|
+
geometry&.respond_to?(symbol) || super
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
5
38
|
# This is a GeoJSON wrapper entity that corresponds to the GeoJSON
|
6
39
|
# "Feature" type. It is an immutable type.
|
7
40
|
#
|
@@ -11,11 +44,12 @@ module RGeo
|
|
11
44
|
# implementation need not subclass or even duck-type this class.
|
12
45
|
# the entity factory mediates all interaction between the GeoJSON
|
13
46
|
# engine and features.
|
14
|
-
|
15
47
|
class Feature
|
48
|
+
include DelegateToGeometry
|
49
|
+
include ConversionMethods
|
50
|
+
|
16
51
|
# Create a feature wrapping the given geometry, with the given ID
|
17
52
|
# and properties.
|
18
|
-
|
19
53
|
def initialize(geometry, id = nil, properties = {})
|
20
54
|
@geometry = geometry
|
21
55
|
@id = id
|
@@ -41,7 +75,6 @@ module RGeo
|
|
41
75
|
# are all equal.
|
42
76
|
# This method uses the eql? method to test geometry equality, which
|
43
77
|
# may behave differently than the == operator.
|
44
|
-
|
45
78
|
def eql?(other)
|
46
79
|
other.is_a?(Feature) && @geometry.eql?(other.geometry) && @id.eql?(other.feature_id) && @properties.eql?(other.instance_variable_get(:@properties))
|
47
80
|
end
|
@@ -50,37 +83,31 @@ module RGeo
|
|
50
83
|
# are all equal.
|
51
84
|
# This method uses the == operator to test geometry equality, which
|
52
85
|
# may behave differently than the eql? method.
|
53
|
-
|
54
86
|
def ==(other)
|
55
87
|
other.is_a?(Feature) && @geometry == other.geometry && @id == other.feature_id && @properties == other.instance_variable_get(:@properties)
|
56
88
|
end
|
57
89
|
|
58
90
|
# Returns the geometry contained in this feature, which may be nil.
|
59
|
-
|
60
91
|
attr_reader :geometry
|
61
92
|
|
62
93
|
# Returns the ID for this feature, which may be nil.
|
63
|
-
|
64
94
|
def feature_id
|
65
95
|
@id
|
66
96
|
end
|
67
97
|
|
68
98
|
# Returns a copy of the properties for this feature.
|
69
|
-
|
70
99
|
def properties
|
71
100
|
@properties.dup
|
72
101
|
end
|
73
102
|
|
74
103
|
# Gets the value of the given named property.
|
75
104
|
# Returns nil if the given property is not found.
|
76
|
-
|
77
105
|
def property(key)
|
78
106
|
@properties[key.to_s]
|
79
107
|
end
|
80
108
|
alias [] property
|
81
109
|
|
82
110
|
# Gets an array of the known property keys in this feature.
|
83
|
-
|
84
111
|
def keys
|
85
112
|
@properties.keys
|
86
113
|
end
|
@@ -95,16 +122,17 @@ module RGeo
|
|
95
122
|
# FeatureCollection implementation need not subclass or even
|
96
123
|
# duck-type this class. The entity factory mediates all interaction
|
97
124
|
# between the GeoJSON engine and feature collections.
|
98
|
-
|
99
125
|
class FeatureCollection
|
100
126
|
include Enumerable
|
127
|
+
include CollectionMethods
|
128
|
+
include ConversionMethods
|
101
129
|
|
102
130
|
# Create a new FeatureCollection with the given features, which must
|
103
131
|
# be provided as an Enumerable.
|
104
|
-
|
105
132
|
def initialize(features = [])
|
106
133
|
@features = []
|
107
134
|
features.each { |f| @features << f if f.is_a?(Feature) }
|
135
|
+
@features.freeze
|
108
136
|
end
|
109
137
|
|
110
138
|
def inspect
|
@@ -123,7 +151,6 @@ module RGeo
|
|
123
151
|
# features in the same order.
|
124
152
|
# This methods uses the eql? method to test geometry equality, which
|
125
153
|
# may behave differently than the == operator.
|
126
|
-
|
127
154
|
def eql?(other)
|
128
155
|
other.is_a?(FeatureCollection) && @features.eql?(other.instance_variable_get(:@features))
|
129
156
|
end
|
@@ -132,25 +159,21 @@ module RGeo
|
|
132
159
|
# features in the same order.
|
133
160
|
# This methods uses the == operator to test geometry equality, which
|
134
161
|
# may behave differently than the eql? method.
|
135
|
-
|
136
162
|
def ==(other)
|
137
163
|
other.is_a?(FeatureCollection) && @features == other.instance_variable_get(:@features)
|
138
164
|
end
|
139
165
|
|
140
166
|
# Iterates or returns an iterator for the features.
|
141
|
-
|
142
167
|
def each(&block)
|
143
168
|
@features.each(&block)
|
144
169
|
end
|
145
170
|
|
146
171
|
# Returns the number of features contained in this collection.
|
147
|
-
|
148
172
|
def size
|
149
173
|
@features.size
|
150
174
|
end
|
151
175
|
|
152
176
|
# Access a feature by index.
|
153
|
-
|
154
177
|
def [](index)
|
155
178
|
@features[index]
|
156
179
|
end
|
@@ -164,60 +187,51 @@ module RGeo
|
|
164
187
|
# Create and return a new feature, given geometry, ID, and
|
165
188
|
# properties hash. Note that, per the GeoJSON spec, geometry and/or
|
166
189
|
# properties may be nil.
|
167
|
-
|
168
190
|
def feature(geometry, id = nil, properties = nil)
|
169
191
|
Feature.new(geometry, id, properties || {})
|
170
192
|
end
|
171
193
|
|
172
194
|
# Create and return a new feature collection, given an enumerable
|
173
195
|
# of feature objects.
|
174
|
-
|
175
196
|
def feature_collection(features = [])
|
176
197
|
FeatureCollection.new(features)
|
177
198
|
end
|
178
199
|
|
179
200
|
# Returns true if the given object is a feature created by this
|
180
201
|
# entity factory.
|
181
|
-
|
182
202
|
def is_feature?(object)
|
183
203
|
object.is_a?(Feature)
|
184
204
|
end
|
185
205
|
|
186
206
|
# Returns true if the given object is a feature collection created
|
187
207
|
# by this entity factory.
|
188
|
-
|
189
208
|
def is_feature_collection?(object)
|
190
209
|
object.is_a?(FeatureCollection)
|
191
210
|
end
|
192
211
|
|
193
212
|
# Run Enumerable#map on the features contained in the given feature
|
194
213
|
# collection.
|
195
|
-
|
196
214
|
def map_feature_collection(object, &block)
|
197
215
|
object.map(&block)
|
198
216
|
end
|
199
217
|
|
200
218
|
# Returns the geometry associated with the given feature.
|
201
|
-
|
202
219
|
def get_feature_geometry(object)
|
203
220
|
object.geometry
|
204
221
|
end
|
205
222
|
|
206
223
|
# Returns the ID of the given feature, or nil for no ID.
|
207
|
-
|
208
224
|
def get_feature_id(object)
|
209
225
|
object.feature_id
|
210
226
|
end
|
211
227
|
|
212
228
|
# Returns the properties of the given feature as a hash. Editing
|
213
229
|
# this hash does not change the state of the feature.
|
214
|
-
|
215
230
|
def get_feature_properties(object)
|
216
231
|
object.properties
|
217
232
|
end
|
218
233
|
|
219
234
|
# Return the singleton instance of EntityFactory.
|
220
|
-
|
221
235
|
def self.instance
|
222
236
|
@instance ||= new
|
223
237
|
end
|
@@ -13,9 +13,8 @@ module RGeo
|
|
13
13
|
# RGeo::GeoJSON::EntityFactory for more information. By default,
|
14
14
|
# encode supports objects of type RGeo::GeoJSON::Feature and
|
15
15
|
# RGeo::GeoJSON::FeatureCollection.
|
16
|
-
|
17
16
|
def encode(object, opts = {})
|
18
|
-
|
17
|
+
coder(opts).encode(object)
|
19
18
|
end
|
20
19
|
|
21
20
|
# High-level convenience routine for decoding an object from GeoJSON.
|
@@ -33,8 +32,8 @@ module RGeo
|
|
33
32
|
# RGeo::GeoJSON::EntityFactory, which generates objects of type
|
34
33
|
# RGeo::GeoJSON::Feature or RGeo::GeoJSON::FeatureCollection.
|
35
34
|
# See RGeo::GeoJSON::EntityFactory for more information.
|
36
|
-
def decode(
|
37
|
-
|
35
|
+
def decode(input, opts = {})
|
36
|
+
coder(opts).decode(input)
|
38
37
|
end
|
39
38
|
|
40
39
|
# Creates and returns a coder object of type RGeo::GeoJSON::Coder
|
data/lib/rgeo/geo_json.rb
CHANGED
@@ -1,8 +1,9 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
require "rgeo"
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
4
|
+
require_relative "geo_json/version"
|
5
|
+
require_relative "geo_json/conversion_methods"
|
6
|
+
require_relative "geo_json/entities"
|
7
|
+
require_relative "geo_json/coder"
|
8
|
+
require_relative "geo_json/interface"
|
9
|
+
require "multi_json"
|
data/lib/rgeo-geojson.rb
CHANGED
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rgeo-geojson
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.
|
4
|
+
version: 2.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Daniel Azuma
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date:
|
12
|
+
date: 2024-07-22 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: rgeo
|
@@ -26,19 +26,19 @@ dependencies:
|
|
26
26
|
- !ruby/object:Gem::Version
|
27
27
|
version: 1.0.0
|
28
28
|
- !ruby/object:Gem::Dependency
|
29
|
-
name:
|
29
|
+
name: multi_json
|
30
30
|
requirement: !ruby/object:Gem::Requirement
|
31
31
|
requirements:
|
32
32
|
- - "~>"
|
33
33
|
- !ruby/object:Gem::Version
|
34
|
-
version: '1.
|
35
|
-
type: :
|
34
|
+
version: '1.15'
|
35
|
+
type: :runtime
|
36
36
|
prerelease: false
|
37
37
|
version_requirements: !ruby/object:Gem::Requirement
|
38
38
|
requirements:
|
39
39
|
- - "~>"
|
40
40
|
- !ruby/object:Gem::Version
|
41
|
-
version: '1.
|
41
|
+
version: '1.15'
|
42
42
|
- !ruby/object:Gem::Dependency
|
43
43
|
name: minitest
|
44
44
|
requirement: !ruby/object:Gem::Requirement
|
@@ -72,6 +72,7 @@ description: Convert RGeo data to and from GeoJSON. rgeo-geojson is an extension
|
|
72
72
|
email:
|
73
73
|
- dazuma@gmail.com
|
74
74
|
- parhameter@gmail.com
|
75
|
+
- kfdoggett@gmail.com
|
75
76
|
executables: []
|
76
77
|
extensions: []
|
77
78
|
extra_rdoc_files: []
|
@@ -82,12 +83,14 @@ files:
|
|
82
83
|
- lib/rgeo-geojson.rb
|
83
84
|
- lib/rgeo/geo_json.rb
|
84
85
|
- lib/rgeo/geo_json/coder.rb
|
86
|
+
- lib/rgeo/geo_json/collection_methods.rb
|
87
|
+
- lib/rgeo/geo_json/conversion_methods.rb
|
85
88
|
- lib/rgeo/geo_json/entities.rb
|
86
89
|
- lib/rgeo/geo_json/interface.rb
|
87
90
|
- lib/rgeo/geo_json/version.rb
|
88
91
|
homepage: https://github.com/rgeo/rgeo-geojson
|
89
92
|
licenses:
|
90
|
-
- BSD
|
93
|
+
- BSD-3-Clause
|
91
94
|
metadata: {}
|
92
95
|
post_install_message:
|
93
96
|
rdoc_options: []
|
@@ -104,8 +107,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
104
107
|
- !ruby/object:Gem::Version
|
105
108
|
version: '0'
|
106
109
|
requirements: []
|
107
|
-
|
108
|
-
rubygems_version: 2.7.8
|
110
|
+
rubygems_version: 3.5.2
|
109
111
|
signing_key:
|
110
112
|
specification_version: 4
|
111
113
|
summary: Convert RGeo data to and from GeoJSON.
|