ffi-ogr 0.1.0.pre → 0.1.0.pre2
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/README.md +32 -15
- data/lib/ffi-ogr.rb +33 -16
- data/lib/ffi-ogr/csv.rb +3 -0
- data/lib/ffi-ogr/data_source.rb +22 -5
- data/lib/ffi-ogr/http_reader.rb +37 -0
- data/lib/ffi-ogr/kml.rb +4 -0
- data/lib/ffi-ogr/reader.rb +8 -14
- data/lib/ffi-ogr/version.rb +1 -1
- data/lib/ffi-ogr/writer.rb +8 -28
- metadata +19 -11
- data/lib/ffi-ogr/feature_service_reader.rb +0 -3
- data/lib/ffi-ogr/generic_reader.rb +0 -9
- data/lib/ffi-ogr/generic_writer.rb +0 -9
- data/lib/ffi-ogr/geo_json_reader.rb +0 -8
- data/lib/ffi-ogr/geo_json_writer.rb +0 -8
- data/lib/ffi-ogr/github_reader.rb +0 -3
- data/lib/ffi-ogr/shp_reader.rb +0 -8
- data/lib/ffi-ogr/shp_writer.rb +0 -8
- data/lib/ffi-ogr/url_geo_json_reader.rb +0 -22
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 05e06c17b1e9e0694b0ff9a7deb4308048ad9f6f
|
4
|
+
data.tar.gz: 89a97fbea029d509c949fc1d8ebd62c22b6a1f46
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: fda92892f274226cce09ee1994aaa774a17dac70e1edcd720d879d872e9f86a70a0c2eae6723fe57cb5a93a0dae888b54aa8ebf96a3f370cdc342372890ac98f
|
7
|
+
data.tar.gz: 55759dbc143c2439baa0dda8e70ba5ac67bb5de3ddf86841c9ed6afecc77bbb9997b1c4524e42cee7220b3758ffce10813d28e3a6b681d53a5a6f296e3012200
|
data/README.md
CHANGED
@@ -1,23 +1,46 @@
|
|
1
|
+
[](https://travis-ci.org/scooterw/ffi-ogr)
|
2
|
+
[](https://codeclimate.com/github/scooterw/ffi-ogr)
|
3
|
+
|
4
|
+
GDAL must be installed:
|
5
|
+
|
6
|
+
Mac:
|
7
|
+
```
|
8
|
+
brew install gdal
|
9
|
+
```
|
10
|
+
|
11
|
+
Ubuntu:
|
12
|
+
```
|
13
|
+
sudo apt-key adv --recv-keys --keyserver keyserver.ubuntu.com 16126D3A3E5C1192
|
14
|
+
sudo apt-get install python-software-properties -y
|
15
|
+
sudo add-apt-repository ppa:ubuntugis/ppa -y
|
16
|
+
sudo apt-get update -qq
|
17
|
+
sudo apt-get install libgdal-dev
|
18
|
+
```
|
19
|
+
|
1
20
|
ffi-ogr
|
2
21
|
... for convenient access to OGR functionality from Ruby
|
3
22
|
|
4
23
|
To run: `bin/ogr_console`
|
5
24
|
|
6
|
-
To read from a known file type (currently SHP, JSON/GeoJSON, raw Github GeoJSON URL, Esri Feature Service URL):
|
25
|
+
To read from a known file type (currently SHP, JSON/GeoJSON, CSV, raw Github GeoJSON URL, raw (spatial) CSV URL, Esri Feature Service URL):
|
7
26
|
|
8
27
|
```ruby
|
9
28
|
data = OGR.read('https://raw.github.com/colemanm/hurricanes/master/fl_2004_hurricanes.geojson')
|
10
29
|
=> #<OGR::DataSource:0x007fb830aa3af8 @ptr=#<FFI::AutoPointer address=0x007fb8311ab990>>
|
11
30
|
|
12
31
|
# output to SHP file
|
13
|
-
data.to_shp '
|
32
|
+
data.to_shp '~/Desktop/github_to_shp.shp'
|
33
|
+
=> nil
|
34
|
+
|
35
|
+
# output to CSV file
|
36
|
+
data.to_csv '~/Desktop/github_to_csv.csv'
|
14
37
|
=> nil
|
15
38
|
```
|
16
39
|
|
17
40
|
To read a shapefile:
|
18
41
|
|
19
42
|
```ruby
|
20
|
-
shp = OGR
|
43
|
+
shp = OGR.read './spec/data/ne_110m_coastline/ne_110m_coastline.shp'
|
21
44
|
# => #<OGR::DataSource:0x007fba4d19c328 @ptr=#<FFI::AutoPointer address=0x007fba4c4cdc50>>
|
22
45
|
|
23
46
|
shp.to_geojson '~/Desktop/output.geojson'
|
@@ -27,7 +50,7 @@ shp.to_geojson '~/Desktop/output.geojson'
|
|
27
50
|
To reproject a shapefile:
|
28
51
|
|
29
52
|
```ruby
|
30
|
-
shp = OGR
|
53
|
+
shp = OGR.read './spec/data/ne_110m_coastline/ne_110m_coastline.shp'
|
31
54
|
# => #<OGR::DataSource:0x007fba4d19c328 @ptr=#<FFI::AutoPointer address=0x007fba4c4cdc50>>
|
32
55
|
|
33
56
|
shp.to_json
|
@@ -44,17 +67,10 @@ shp.to_shp '~/Desktop/reprojected_shp.shp', {spatial_ref: new_sr}
|
|
44
67
|
# => Output reprojected SHP to specified file
|
45
68
|
```
|
46
69
|
|
47
|
-
A reader may also be inferred by file extension (currently works for shp and json/geojson):
|
48
|
-
|
49
|
-
```ruby
|
50
|
-
shp = OGR::Reader.from_file_type './spec/data/ne_110m_coastline/ne_110m_coastline.shp'
|
51
|
-
```
|
52
|
-
|
53
70
|
To create a shapefile:
|
54
71
|
|
55
72
|
```ruby
|
56
|
-
writer = OGR
|
57
|
-
writer.set_output '~/Documents/shapefiles/my_new.shp'
|
73
|
+
writer = OGR.create_writer '~/Documents/shapefiles/my_new.shp'
|
58
74
|
|
59
75
|
shp = writer.ptr
|
60
76
|
|
@@ -84,10 +100,11 @@ layer.add_feature feature
|
|
84
100
|
layer.sync
|
85
101
|
```
|
86
102
|
|
87
|
-
A writer may
|
103
|
+
A writer may be fetched by driver type:
|
88
104
|
|
89
105
|
```ruby
|
90
|
-
writer = OGR
|
106
|
+
writer = OGR.get_writer 'shp'
|
107
|
+
writer.set_output '~/Documents/shapefiles/my_new.shp'
|
91
108
|
```
|
92
109
|
|
93
|
-
Tested on: MRI 1.9.
|
110
|
+
Tested on: MRI (1.9/2.0), JRuby (1.9/2.0), and Rubinius (1.9/2.0)
|
data/lib/ffi-ogr.rb
CHANGED
@@ -6,23 +6,21 @@ module OGR
|
|
6
6
|
|
7
7
|
DRIVER_TYPES = {
|
8
8
|
'shapefile' => 'ESRI Shapefile',
|
9
|
-
'
|
9
|
+
'shp' => 'ESRI Shapefile',
|
10
|
+
'geojson' => 'GeoJSON',
|
11
|
+
'json' => 'GeoJSON',
|
12
|
+
'csv' => 'CSV',
|
13
|
+
'kml' => 'KML'
|
10
14
|
}
|
11
15
|
|
12
16
|
autoload :Reader, File.join(OGR_BASE, 'reader')
|
13
|
-
autoload :
|
14
|
-
autoload :ShpReader, File.join(OGR_BASE, 'shp_reader')
|
15
|
-
autoload :GeoJSONReader, File.join(OGR_BASE, 'geo_json_reader')
|
16
|
-
autoload :UrlGeoJSONReader, File.join(OGR_BASE, 'url_geo_json_reader')
|
17
|
-
autoload :FeatureServiceReader, File.join(OGR_BASE, 'feature_service_reader')
|
18
|
-
autoload :GithubReader, File.join(OGR_BASE, 'github_reader')
|
17
|
+
autoload :HttpReader, File.join(OGR_BASE, 'http_reader')
|
19
18
|
autoload :Writer, File.join(OGR_BASE, 'writer')
|
20
|
-
autoload :GenericWriter, File.join(OGR_BASE, 'generic_writer')
|
21
|
-
autoload :ShpWriter, File.join(OGR_BASE, 'shp_writer')
|
22
|
-
autoload :GeoJSONWriter, File.join(OGR_BASE, 'geo_json_writer')
|
23
19
|
autoload :DataSource, File.join(OGR_BASE, 'data_source')
|
24
20
|
autoload :Shapefile, File.join(OGR_BASE, 'shapefile')
|
25
21
|
autoload :GeoJSON, File.join(OGR_BASE, 'geo_json')
|
22
|
+
autoload :CSV, File.join(OGR_BASE, 'csv')
|
23
|
+
autoload :KML, File.join(OGR_BASE, 'kml')
|
26
24
|
autoload :Tools, File.join(OGR_BASE, 'tools')
|
27
25
|
autoload :Layer, File.join(OGR_BASE, 'layer')
|
28
26
|
autoload :Feature, File.join(OGR_BASE, 'feature')
|
@@ -341,17 +339,36 @@ module OGR
|
|
341
339
|
FFI::MemoryPointer.from_string(str)
|
342
340
|
end
|
343
341
|
|
342
|
+
def get_writer(source)
|
343
|
+
extension = source.split('.').last
|
344
|
+
driver = DRIVER_TYPES[extension]
|
345
|
+
|
346
|
+
raise RuntimeError.new "Could not find appropriate driver" if driver.nil?
|
347
|
+
|
348
|
+
Writer.new(driver)
|
349
|
+
end
|
350
|
+
|
351
|
+
def create_writer(path)
|
352
|
+
raise RuntimeError.new "Path already exists: #{path}" if File.exists?(path)
|
353
|
+
|
354
|
+
writer = get_writer path
|
355
|
+
writer.set_output path
|
356
|
+
writer
|
357
|
+
end
|
358
|
+
|
344
359
|
def read(source)
|
345
360
|
case source
|
346
361
|
when /http:|https:/
|
347
|
-
|
348
|
-
when /.shp/
|
349
|
-
ShpReader.new.read source
|
350
|
-
when /.json|.geojson/
|
351
|
-
GeoJSONReader.new.read source
|
362
|
+
HttpReader.new.read source
|
352
363
|
else
|
353
|
-
|
364
|
+
extension = source.split('.').last
|
365
|
+
driver = DRIVER_TYPES[extension]
|
366
|
+
|
367
|
+
raise RuntimeError.new "Could not determine file type" if driver.nil?
|
368
|
+
|
369
|
+
Reader.new(driver).read source
|
354
370
|
end
|
355
371
|
end
|
356
372
|
end
|
357
373
|
end
|
374
|
+
|
data/lib/ffi-ogr/csv.rb
ADDED
data/lib/ffi-ogr/data_source.rb
CHANGED
@@ -129,18 +129,35 @@ module OGR
|
|
129
129
|
end
|
130
130
|
alias_method :fields, :get_fields
|
131
131
|
|
132
|
-
def
|
132
|
+
def to_format(format, output_path, spatial_ref=nil)
|
133
133
|
raise RuntimeError.new("Output path not specified.") if output_path.nil?
|
134
134
|
|
135
135
|
# TODO: handle parsing of spatial_ref -> copy options
|
136
136
|
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
|
137
|
+
unless spatial_ref
|
138
|
+
copy format, output_path, spatial_ref
|
139
|
+
else
|
140
|
+
if spatial_ref[:spatial_ref].instance_of? OGR::SpatialReference
|
141
|
+
copy_with_transform format, output_path, spatial_ref[:spatial_ref]
|
142
|
+
else
|
143
|
+
raise RuntimeError.new("Invalid spatial reference specified.")
|
144
|
+
end
|
141
145
|
end
|
142
146
|
end
|
143
147
|
|
148
|
+
def to_shp(output_path, spatial_ref=nil)
|
149
|
+
to_format('shapefile', output_path, spatial_ref)
|
150
|
+
end
|
151
|
+
|
152
|
+
def to_csv(output_path, spatial_ref=nil)
|
153
|
+
to_format('csv', output_path, spatial_ref)
|
154
|
+
end
|
155
|
+
|
156
|
+
def to_kml(output_path, spatial_ref=nil)
|
157
|
+
warn "KML output will always be in EPSG:4326" unless spatial_ref.nil?
|
158
|
+
to_format('kml', output_path, spatial_ref)
|
159
|
+
end
|
160
|
+
|
144
161
|
def to_geojson(output_path, options=nil)
|
145
162
|
raise RuntimeError.new("Output path not specified.") if output_path.nil?
|
146
163
|
|
@@ -0,0 +1,37 @@
|
|
1
|
+
require 'fileutils'
|
2
|
+
require 'securerandom'
|
3
|
+
require 'faraday'
|
4
|
+
|
5
|
+
module OGR
|
6
|
+
class HttpReader
|
7
|
+
def read(url, writeable=false)
|
8
|
+
file_extension = url.split('.').last
|
9
|
+
driver = OGR::DRIVER_TYPES[file_extension]
|
10
|
+
|
11
|
+
if driver.nil?
|
12
|
+
unless url =~ /FeatureServer/
|
13
|
+
raise RuntimeError.new "File type not supported."
|
14
|
+
else
|
15
|
+
# ? assume Esri Feature Service ?
|
16
|
+
file_extension = 'json'
|
17
|
+
driver = OGR::DRIVER_TYPES[file_extension]
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
file_name = "#{SecureRandom.urlsafe_base64}.#{file_extension}"
|
22
|
+
|
23
|
+
http_resource = Faraday.get(url).body
|
24
|
+
|
25
|
+
File.open(file_name, 'wb') do |f|
|
26
|
+
f.write http_resource
|
27
|
+
end
|
28
|
+
|
29
|
+
ds = Reader.new(driver).read(file_name, writeable)
|
30
|
+
|
31
|
+
FileUtils.rm file_name
|
32
|
+
|
33
|
+
ds
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
data/lib/ffi-ogr/kml.rb
ADDED
data/lib/ffi-ogr/reader.rb
CHANGED
@@ -2,6 +2,8 @@ module OGR
|
|
2
2
|
class Reader
|
3
3
|
include OGR::FFIOGR
|
4
4
|
|
5
|
+
attr_accessor :type
|
6
|
+
|
5
7
|
TF_MAP = {
|
6
8
|
true => 1,
|
7
9
|
false => 0,
|
@@ -9,20 +11,11 @@ module OGR
|
|
9
11
|
0 => false
|
10
12
|
}
|
11
13
|
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
path = File.expand_path(path)
|
18
|
-
|
19
|
-
if path =~ /.shp/
|
20
|
-
ShpReader.new
|
21
|
-
elsif path =~ /.geojson|.json/
|
22
|
-
GeoJSONReader.new
|
23
|
-
else
|
24
|
-
raise RuntimeError.new("Could not determine appropriate reader for this file type")
|
25
|
-
end
|
14
|
+
def initialize(driver_name)
|
15
|
+
OGRRegisterAll()
|
16
|
+
@driver = OGRGetDriverByName(driver_name)
|
17
|
+
raise RuntimeError.new "Invalid driver name" if @driver.null?
|
18
|
+
@type = driver_name
|
26
19
|
end
|
27
20
|
|
28
21
|
def read(file_path, writeable=false)
|
@@ -31,3 +24,4 @@ module OGR
|
|
31
24
|
end
|
32
25
|
end
|
33
26
|
end
|
27
|
+
|
data/lib/ffi-ogr/version.rb
CHANGED
data/lib/ffi-ogr/writer.rb
CHANGED
@@ -2,9 +2,14 @@ module OGR
|
|
2
2
|
class Writer
|
3
3
|
include OGR::FFIOGR
|
4
4
|
|
5
|
-
attr_accessor :ptr
|
5
|
+
attr_accessor :ptr, :type
|
6
6
|
|
7
|
-
def initialize
|
7
|
+
def initialize(driver_name)
|
8
|
+
OGRRegisterAll()
|
9
|
+
@driver = OGRGetDriverByName(driver_name)
|
10
|
+
raise RuntimeError.new "Invalid driver name" if @driver.null?
|
11
|
+
@type = driver_name
|
12
|
+
end
|
8
13
|
|
9
14
|
def set_output(path, options={})
|
10
15
|
path = File.expand_path(path)
|
@@ -12,31 +17,6 @@ module OGR
|
|
12
17
|
@ptr = OGR::Tools.cast_data_source(ds)
|
13
18
|
@ptr
|
14
19
|
end
|
15
|
-
|
16
|
-
def self.from_file_type(path)
|
17
|
-
path = File.expand_path(path)
|
18
|
-
|
19
|
-
unless File.exists? path
|
20
|
-
if path =~ /.shp/
|
21
|
-
writer = ShpWriter.new
|
22
|
-
elsif path =~ /.geojson|.json/
|
23
|
-
writer = GeoJSONWriter.new
|
24
|
-
else
|
25
|
-
raise RuntimeError.new("Could not determine appropriate writer for this file type")
|
26
|
-
end
|
27
|
-
|
28
|
-
writer.set_output(path)
|
29
|
-
writer
|
30
|
-
else
|
31
|
-
raise RuntimeError.new("Path already exists: #{path}")
|
32
|
-
end
|
33
|
-
end
|
34
|
-
|
35
|
-
def export(output_path)
|
36
|
-
writer = Writer.from_file_type output_path
|
37
|
-
data_source = writer.ds
|
38
|
-
|
39
|
-
# @ptr -> data_source
|
40
|
-
end
|
41
20
|
end
|
42
21
|
end
|
22
|
+
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: ffi-ogr
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.0.
|
4
|
+
version: 0.1.0.pre2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Scooter Wadsworth
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2013-
|
11
|
+
date: 2013-11-08 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: ffi
|
@@ -80,6 +80,20 @@ dependencies:
|
|
80
80
|
- - '>='
|
81
81
|
- !ruby/object:Gem::Version
|
82
82
|
version: '0'
|
83
|
+
- !ruby/object:Gem::Dependency
|
84
|
+
name: simplecov
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - '>='
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: '0'
|
90
|
+
type: :development
|
91
|
+
prerelease: false
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
93
|
+
requirements:
|
94
|
+
- - '>='
|
95
|
+
- !ruby/object:Gem::Version
|
96
|
+
version: '0'
|
83
97
|
description: FFI wrapper for OGR
|
84
98
|
email:
|
85
99
|
- scooterwadsworth@gmail.com
|
@@ -91,19 +105,16 @@ files:
|
|
91
105
|
- README.md
|
92
106
|
- bin/ogr_console
|
93
107
|
- lib/ffi-ogr/coordinate_transformation.rb
|
108
|
+
- lib/ffi-ogr/csv.rb
|
94
109
|
- lib/ffi-ogr/data_source.rb
|
95
110
|
- lib/ffi-ogr/envelope.rb
|
96
111
|
- lib/ffi-ogr/feature.rb
|
97
|
-
- lib/ffi-ogr/feature_service_reader.rb
|
98
|
-
- lib/ffi-ogr/generic_reader.rb
|
99
|
-
- lib/ffi-ogr/generic_writer.rb
|
100
112
|
- lib/ffi-ogr/geo_json.rb
|
101
|
-
- lib/ffi-ogr/geo_json_reader.rb
|
102
|
-
- lib/ffi-ogr/geo_json_writer.rb
|
103
113
|
- lib/ffi-ogr/geometry.rb
|
104
114
|
- lib/ffi-ogr/geometry_collection.rb
|
105
115
|
- lib/ffi-ogr/geometry_collection_25d.rb
|
106
|
-
- lib/ffi-ogr/
|
116
|
+
- lib/ffi-ogr/http_reader.rb
|
117
|
+
- lib/ffi-ogr/kml.rb
|
107
118
|
- lib/ffi-ogr/layer.rb
|
108
119
|
- lib/ffi-ogr/line_string.rb
|
109
120
|
- lib/ffi-ogr/line_string_25d.rb
|
@@ -121,11 +132,8 @@ files:
|
|
121
132
|
- lib/ffi-ogr/polygon_25d.rb
|
122
133
|
- lib/ffi-ogr/reader.rb
|
123
134
|
- lib/ffi-ogr/shapefile.rb
|
124
|
-
- lib/ffi-ogr/shp_reader.rb
|
125
|
-
- lib/ffi-ogr/shp_writer.rb
|
126
135
|
- lib/ffi-ogr/spatial_reference.rb
|
127
136
|
- lib/ffi-ogr/tools.rb
|
128
|
-
- lib/ffi-ogr/url_geo_json_reader.rb
|
129
137
|
- lib/ffi-ogr/version.rb
|
130
138
|
- lib/ffi-ogr/writer.rb
|
131
139
|
- lib/ffi-ogr.rb
|
data/lib/ffi-ogr/shp_reader.rb
DELETED
data/lib/ffi-ogr/shp_writer.rb
DELETED
@@ -1,22 +0,0 @@
|
|
1
|
-
require 'fileutils'
|
2
|
-
require 'securerandom'
|
3
|
-
require 'faraday'
|
4
|
-
|
5
|
-
module OGR
|
6
|
-
class UrlGeoJSONReader < GeoJSONReader
|
7
|
-
def read(url, writeable=false)
|
8
|
-
file_name = "#{SecureRandom.urlsafe_base64}.json"
|
9
|
-
remote_json = Faraday.get(url).body
|
10
|
-
|
11
|
-
File.open(file_name, 'wb') do |f|
|
12
|
-
f.write(remote_json)
|
13
|
-
end
|
14
|
-
|
15
|
-
data_source = super(file_name, writeable)
|
16
|
-
|
17
|
-
FileUtils.rm(file_name)
|
18
|
-
|
19
|
-
data_source
|
20
|
-
end
|
21
|
-
end
|
22
|
-
end
|