open311 0.0.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.
- data/.gitignore +8 -0
- data/.rspec +3 -0
- data/.yardopts +7 -0
- data/Gemfile +4 -0
- data/Gemfile.lock +66 -0
- data/LICENSE.mkd +20 -0
- data/README.mkd +71 -0
- data/Rakefile +34 -0
- data/autotest/discover.rb +1 -0
- data/lib/faraday/multipart.rb +29 -0
- data/lib/faraday/raise_error.rb +40 -0
- data/lib/open311.rb +46 -0
- data/lib/open311/client.rb +19 -0
- data/lib/open311/client/connection.rb +28 -0
- data/lib/open311/client/request.rb +40 -0
- data/lib/open311/client/service.rb +21 -0
- data/lib/open311/configuration.rb +41 -0
- data/lib/open311/version.rb +3 -0
- data/open311.gemspec +36 -0
- data/spec/fixtures/services.xml +30 -0
- data/spec/open311_spec.rb +27 -0
- data/spec/spec_helper.rb +14 -0
- metadata +312 -0
data/.gitignore
ADDED
data/.rspec
ADDED
data/.yardopts
ADDED
data/Gemfile
ADDED
data/Gemfile.lock
ADDED
@@ -0,0 +1,66 @@
|
|
1
|
+
PATH
|
2
|
+
remote: .
|
3
|
+
specs:
|
4
|
+
open311 (0.0.0)
|
5
|
+
faraday (~> 0.5.2)
|
6
|
+
faraday_middleware (~> 0.2.3)
|
7
|
+
hashie (~> 0.4.0)
|
8
|
+
multi_json (~> 0.0.5)
|
9
|
+
multi_xml (~> 0.2.0)
|
10
|
+
|
11
|
+
GEM
|
12
|
+
remote: http://rubygems.org/
|
13
|
+
specs:
|
14
|
+
ZenTest (4.4.0)
|
15
|
+
addressable (2.2.2)
|
16
|
+
crack (0.1.8)
|
17
|
+
diff-lcs (1.1.2)
|
18
|
+
faraday (0.5.2)
|
19
|
+
addressable (~> 2.2.2)
|
20
|
+
multipart-post (~> 1.0.1)
|
21
|
+
rack (>= 1.1.0, < 2)
|
22
|
+
faraday_middleware (0.2.3)
|
23
|
+
faraday (~> 0.5.2)
|
24
|
+
hashie (0.4.0)
|
25
|
+
libxml-ruby (1.1.4)
|
26
|
+
multi_json (0.0.5)
|
27
|
+
multi_xml (0.2.0)
|
28
|
+
multipart-post (1.0.1)
|
29
|
+
rack (1.2.1)
|
30
|
+
rake (0.8.7)
|
31
|
+
rcov (0.9.9)
|
32
|
+
rspec (2.0.1)
|
33
|
+
rspec-core (~> 2.0.1)
|
34
|
+
rspec-expectations (~> 2.0.1)
|
35
|
+
rspec-mocks (~> 2.0.1)
|
36
|
+
rspec-core (2.0.1)
|
37
|
+
rspec-expectations (2.0.1)
|
38
|
+
diff-lcs (>= 1.1.2)
|
39
|
+
rspec-mocks (2.0.1)
|
40
|
+
rspec-core (~> 2.0.1)
|
41
|
+
rspec-expectations (~> 2.0.1)
|
42
|
+
webmock (1.5.0)
|
43
|
+
addressable (>= 2.2.2)
|
44
|
+
crack (>= 0.1.7)
|
45
|
+
yajl-ruby (0.7.8)
|
46
|
+
yard (0.6.1)
|
47
|
+
|
48
|
+
PLATFORMS
|
49
|
+
ruby
|
50
|
+
|
51
|
+
DEPENDENCIES
|
52
|
+
ZenTest (~> 4.4)
|
53
|
+
bundler (~> 1.0)
|
54
|
+
faraday (~> 0.5.2)
|
55
|
+
faraday_middleware (~> 0.2.3)
|
56
|
+
hashie (~> 0.4.0)
|
57
|
+
libxml-ruby (~> 1.1)
|
58
|
+
multi_json (~> 0.0.5)
|
59
|
+
multi_xml (~> 0.2.0)
|
60
|
+
open311!
|
61
|
+
rake (~> 0.8)
|
62
|
+
rcov (~> 0.9)
|
63
|
+
rspec (~> 2.0.1)
|
64
|
+
webmock (~> 1.5)
|
65
|
+
yajl-ruby (~> 0.7)
|
66
|
+
yard (~> 0.6)
|
data/LICENSE.mkd
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2010 Code for America Laboratories
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.mkd
ADDED
@@ -0,0 +1,71 @@
|
|
1
|
+
Open311
|
2
|
+
=======
|
3
|
+
A Ruby wrapper for the Open311 API v2.
|
4
|
+
|
5
|
+
Does your project or company use this gem?
|
6
|
+
------------------------------------------
|
7
|
+
Add it to the [apps](http://github.com/cfalabs/open311/wiki/apps) wiki!
|
8
|
+
|
9
|
+
Installation
|
10
|
+
------------
|
11
|
+
$ [sudo] gem install open311
|
12
|
+
|
13
|
+
Documentation
|
14
|
+
-------------
|
15
|
+
<http://rdoc.info/gems/open311>
|
16
|
+
|
17
|
+
Usage Examples
|
18
|
+
--------------
|
19
|
+
require 'open311'
|
20
|
+
|
21
|
+
# Certain methods require an API key
|
22
|
+
Open311.configure do |config|
|
23
|
+
config.api_key = YOUR_API_KEY
|
24
|
+
config.endpoint = 'https://open311.sfgov.org/'
|
25
|
+
config.jurisdiction = 'sfgov.org'
|
26
|
+
end
|
27
|
+
|
28
|
+
# Provide a list of acceptable 311 service request types and their associated service codes
|
29
|
+
Open311.service_list
|
30
|
+
|
31
|
+
Contributing
|
32
|
+
------------
|
33
|
+
In the spirit of [free software](http://www.fsf.org/licensing/essays/free-sw.html), **everyone** is encouraged to help improve this project.
|
34
|
+
|
35
|
+
Here are some ways *you* can contribute:
|
36
|
+
|
37
|
+
* by using alpha, beta, and prerelease versions
|
38
|
+
* by reporting bugs
|
39
|
+
* by suggesting new features
|
40
|
+
* by writing or editing documentation
|
41
|
+
* by writing specifications
|
42
|
+
* by writing code (**no patch is too small**: fix typos, add comments, clean up inconsistent whitespace)
|
43
|
+
* by refactoring code
|
44
|
+
* by resolving [issues](http://github.com/cfalabs/open311/issues)
|
45
|
+
* by reviewing patches
|
46
|
+
|
47
|
+
Submitting an Issue
|
48
|
+
-------------------
|
49
|
+
We use the [GitHub issue tracker](http://github.com/cfalabs/open311/issues) to track bugs and
|
50
|
+
features. Before submitting a bug report or feature request, check to make sure it hasn't already
|
51
|
+
been submitted. You can indicate support for an existing issuse by voting it up. When submitting a
|
52
|
+
bug report, please include a [Gist](http://gist.github.com/) that includes a stack trace and any
|
53
|
+
details that may be necessary to reproduce the bug, including your gem version, Ruby version, and
|
54
|
+
operating system. Ideally, a bug report should include a pull request with failing specs.
|
55
|
+
|
56
|
+
Submitting a Pull Request
|
57
|
+
-------------------------
|
58
|
+
1. Fork the project.
|
59
|
+
2. Create a topic branch.
|
60
|
+
3. Implement your feature or bug fix.
|
61
|
+
4. Add documentation for your feature or bug fix.
|
62
|
+
5. Run <tt>bundle exec rake doc:yard</tt>. If your changes are not 100% documented, go back to step 4.
|
63
|
+
6. Add specs for your feature or bug fix.
|
64
|
+
7. Run <tt>bundle exec rake spec:rcov</tt>. If your changes are not 100% covered, go back to step 6.
|
65
|
+
8. Commit and push your changes.
|
66
|
+
9. Submit a pull request. Please do not include changes to the gemspec, version, or history file. (If you want to create your own version for some reason, please do so in a separate commit.)
|
67
|
+
|
68
|
+
Copyright
|
69
|
+
---------
|
70
|
+
Copyright (c) 2010 Code for America Laboratories
|
71
|
+
See [LICENSE](https://github.com/cfalabs/open311/blob/master/LICENSE.mkd) for details.
|
data/Rakefile
ADDED
@@ -0,0 +1,34 @@
|
|
1
|
+
require 'bundler'
|
2
|
+
Bundler::GemHelper.install_tasks
|
3
|
+
|
4
|
+
require 'rspec/core/rake_task'
|
5
|
+
RSpec::Core::RakeTask.new(:spec)
|
6
|
+
|
7
|
+
namespace :spec do
|
8
|
+
desc "Run all examples using rcov"
|
9
|
+
RSpec::Core::RakeTask.new(:rcov => :cleanup_rcov_files) do |task|
|
10
|
+
task.rcov = true
|
11
|
+
task.rcov_opts = %[-Ilib -Ispec --exclude "gems/*,features,specs" --text-report --sort coverage]
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
task :cleanup_rcov_files do
|
16
|
+
rm_rf 'coverage'
|
17
|
+
end
|
18
|
+
|
19
|
+
task :default => ["spec:rcov"]
|
20
|
+
|
21
|
+
namespace :doc do
|
22
|
+
require 'yard'
|
23
|
+
YARD::Rake::YardocTask.new do |task|
|
24
|
+
task.files = ['LICENSE.mkd', 'lib/**/*.rb']
|
25
|
+
task.options = [
|
26
|
+
'--no-private',
|
27
|
+
'--protected',
|
28
|
+
'--output-dir', 'doc/yard',
|
29
|
+
'--tag', 'format:Supported formats',
|
30
|
+
'--tag', 'key:Requires API key',
|
31
|
+
'--markup', 'markdown',
|
32
|
+
]
|
33
|
+
end
|
34
|
+
end
|
@@ -0,0 +1 @@
|
|
1
|
+
Autotest.add_discovery { "rspec2" }
|
@@ -0,0 +1,29 @@
|
|
1
|
+
require 'faraday'
|
2
|
+
|
3
|
+
# @api private
|
4
|
+
module Faraday
|
5
|
+
class Request::Multipart < Faraday::Middleware
|
6
|
+
def call(env)
|
7
|
+
if env[:body].is_a?(Hash)
|
8
|
+
env[:body].each do |key, value|
|
9
|
+
if value.is_a?(File)
|
10
|
+
env[:body][key] = Faraday::UploadIO.new(value, mime_type(value), value.path)
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
@app.call(env)
|
16
|
+
end
|
17
|
+
|
18
|
+
private
|
19
|
+
|
20
|
+
def mime_type(file)
|
21
|
+
case file.path
|
22
|
+
when /\.jpe?g/i then 'image/jpeg'
|
23
|
+
when /\.gif$/i then 'image/gif'
|
24
|
+
when /\.png$/i then 'image/png'
|
25
|
+
else 'application/octet-stream'
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
@@ -0,0 +1,40 @@
|
|
1
|
+
require 'faraday'
|
2
|
+
|
3
|
+
# @api private
|
4
|
+
module Faraday
|
5
|
+
class Response::RaiseError < Response::Middleware
|
6
|
+
def self.register_on_complete(env)
|
7
|
+
env[:response].on_complete do |response|
|
8
|
+
case response[:status].to_i
|
9
|
+
when 400
|
10
|
+
raise Open311::BadRequest, error_message(response)
|
11
|
+
when 401
|
12
|
+
raise Open311::Unauthorized, error_message(response)
|
13
|
+
when 403
|
14
|
+
raise Open311::Forbidden, error_message(response)
|
15
|
+
when 404
|
16
|
+
raise Open311::NotFound, error_message(response)
|
17
|
+
when 406
|
18
|
+
raise Open311::NotAcceptable, error_message(response)
|
19
|
+
when 500
|
20
|
+
raise Open311::InternalServerError, error_message(response)
|
21
|
+
when 502
|
22
|
+
raise Open311::BadGateway, error_message(response)
|
23
|
+
when 503
|
24
|
+
raise Open311::ServiceUnavailable, error_message(response)
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
def initialize(app)
|
30
|
+
super
|
31
|
+
@parser = nil
|
32
|
+
end
|
33
|
+
|
34
|
+
private
|
35
|
+
|
36
|
+
def self.error_message(response)
|
37
|
+
"#{response[:method].to_s.upcase} #{response[:url].to_s}: #{response[:response_headers]['status']}#{(': ' + response[:body]['error']) if response[:body] && response[:body]['error']}"
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
data/lib/open311.rb
ADDED
@@ -0,0 +1,46 @@
|
|
1
|
+
require File.expand_path('../open311/configuration', __FILE__)
|
2
|
+
require File.expand_path('../open311/client', __FILE__)
|
3
|
+
|
4
|
+
module Open311
|
5
|
+
extend Configuration
|
6
|
+
|
7
|
+
# Alias for Open311::Client.new
|
8
|
+
#
|
9
|
+
# @return [Open311::Client]
|
10
|
+
def self.client(options={})
|
11
|
+
Open311::Client.new(options)
|
12
|
+
end
|
13
|
+
|
14
|
+
# Delegate to Open311::Client
|
15
|
+
def self.method_missing(method, *args, &block)
|
16
|
+
return super unless client.respond_to?(method)
|
17
|
+
client.send(method, *args, &block)
|
18
|
+
end
|
19
|
+
|
20
|
+
# Custom error class for rescuing from all Open311 errors
|
21
|
+
class Error < StandardError; end
|
22
|
+
|
23
|
+
# Raised when Open311 returns a 400 HTTP status code
|
24
|
+
class BadRequest < Error; end
|
25
|
+
|
26
|
+
# Raised when Open311 returns a 401 HTTP status code
|
27
|
+
class Unauthorized < Error; end
|
28
|
+
|
29
|
+
# Raised when Open311 returns a 403 HTTP status code
|
30
|
+
class Forbidden < Error; end
|
31
|
+
|
32
|
+
# Raised when Open311 returns a 404 HTTP status code
|
33
|
+
class NotFound < Error; end
|
34
|
+
|
35
|
+
# Raised when Open311 returns a 406 HTTP status code
|
36
|
+
class NotAcceptable < Error; end
|
37
|
+
|
38
|
+
# Raised when Open311 returns a 500 HTTP status code
|
39
|
+
class InternalServerError < Error; end
|
40
|
+
|
41
|
+
# Raised when Open311 returns a 502 HTTP status code
|
42
|
+
class BadGateway < Error; end
|
43
|
+
|
44
|
+
# Raised when Open311 returns a 503 HTTP status code
|
45
|
+
class ServiceUnavailable < Error; end
|
46
|
+
end
|
@@ -0,0 +1,19 @@
|
|
1
|
+
Dir[File.expand_path('../client/*.rb', __FILE__)].each{|file| require file}
|
2
|
+
|
3
|
+
module Open311
|
4
|
+
class Client
|
5
|
+
attr_accessor *Configuration::VALID_OPTIONS_KEYS
|
6
|
+
|
7
|
+
def initialize(options={})
|
8
|
+
options = Open311.options.merge(options)
|
9
|
+
Configuration::VALID_OPTIONS_KEYS.each do |key|
|
10
|
+
send("#{key}=", options[key])
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
include Open311::Client::Connection
|
15
|
+
include Open311::Client::Request
|
16
|
+
|
17
|
+
include Open311::Client::Service
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,28 @@
|
|
1
|
+
require 'faraday_middleware'
|
2
|
+
Dir[File.expand_path('../../../faraday/*.rb', __FILE__)].each{|file| require file}
|
3
|
+
|
4
|
+
module Open311
|
5
|
+
class Client
|
6
|
+
# @private
|
7
|
+
module Connection
|
8
|
+
private
|
9
|
+
|
10
|
+
def connection(raw=false)
|
11
|
+
options = {
|
12
|
+
# :headers => {'Accept' => "*/#{format}", 'User-Agent' => user_agent},
|
13
|
+
:proxy => proxy,
|
14
|
+
:ssl => {:verify => false},
|
15
|
+
:url => endpoint
|
16
|
+
}
|
17
|
+
|
18
|
+
Faraday::Connection.new(options) do |builder|
|
19
|
+
builder.use Faraday::Request::Multipart
|
20
|
+
builder.adapter(adapter)
|
21
|
+
builder.use Faraday::Response::RaiseError
|
22
|
+
builder.use Faraday::Response::Parse unless raw
|
23
|
+
builder.use Faraday::Response::Mashify unless raw
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,40 @@
|
|
1
|
+
module Open311
|
2
|
+
class Client
|
3
|
+
module Request
|
4
|
+
def get(path, options={}, raw=false)
|
5
|
+
request(:get, path, options, raw)
|
6
|
+
end
|
7
|
+
|
8
|
+
def post(path, options={}, raw=false)
|
9
|
+
request(:post, path, options, raw)
|
10
|
+
end
|
11
|
+
|
12
|
+
def put(path, options={}, raw=false)
|
13
|
+
request(:put, path, options, raw)
|
14
|
+
end
|
15
|
+
|
16
|
+
def delete(path, options={}, raw=false)
|
17
|
+
request(:delete, path, options, raw)
|
18
|
+
end
|
19
|
+
|
20
|
+
private
|
21
|
+
|
22
|
+
def request(method, path, options, raw)
|
23
|
+
response = connection(raw).send(method) do |request|
|
24
|
+
case method
|
25
|
+
when :get, :delete
|
26
|
+
request.url(formatted_path(path), options)
|
27
|
+
when :post, :put
|
28
|
+
request.path = formatted_path(path)
|
29
|
+
request.body = options
|
30
|
+
end
|
31
|
+
end
|
32
|
+
raw ? response : response.body
|
33
|
+
end
|
34
|
+
|
35
|
+
def formatted_path(path)
|
36
|
+
[path, format].compact.join('.')
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
module Open311
|
2
|
+
class Client
|
3
|
+
module Service
|
4
|
+
# Provide a list of acceptable 311 service request types and their associated service codes
|
5
|
+
#
|
6
|
+
# @todo Overload the method to allow fetching of the authenticated user's screen name from configurati
|
7
|
+
# @format :xml
|
8
|
+
# @key false
|
9
|
+
# @param options [Hash] A customizable set of options.
|
10
|
+
# @return [Array]
|
11
|
+
# @see http://wiki.open311.org/GeoReport_v2#GET_Service_List
|
12
|
+
# @example Provide a list of acceptable 311 service request types and their associated service codes
|
13
|
+
# Open311.service_list
|
14
|
+
def service_list(options={})
|
15
|
+
options.merge!(:jurisdiction_id => jurisdiction)
|
16
|
+
response = get('dev/v2/services', options)
|
17
|
+
format.to_s.downcase == 'xml' ? response['services']['service'] : response
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
require 'faraday'
|
2
|
+
require File.expand_path('../version', __FILE__)
|
3
|
+
|
4
|
+
module Open311
|
5
|
+
module Configuration
|
6
|
+
VALID_OPTIONS_KEYS = [:adapter, :api_key, :endpoint, :format, :jurisdiction, :proxy, :user_agent].freeze
|
7
|
+
VALID_FORMATS = [:json, :xml].freeze
|
8
|
+
|
9
|
+
DEFAULT_ADAPTER = Faraday.default_adapter.freeze
|
10
|
+
DEFAULT_API_KEY = nil.freeze
|
11
|
+
DEFAULT_ENDPOINT = nil.freeze
|
12
|
+
DEFAULT_FORMAT = :json.freeze
|
13
|
+
DEFAULT_JURISDICTION = nil.freeze
|
14
|
+
DEFAULT_PROXY = nil.freeze
|
15
|
+
DEFAULT_USER_AGENT = "Open311 Ruby Gem #{Open311::VERSION}".freeze
|
16
|
+
|
17
|
+
attr_accessor *VALID_OPTIONS_KEYS
|
18
|
+
|
19
|
+
def self.extended(base)
|
20
|
+
base.reset
|
21
|
+
end
|
22
|
+
|
23
|
+
def configure
|
24
|
+
yield self
|
25
|
+
end
|
26
|
+
|
27
|
+
def options
|
28
|
+
VALID_OPTIONS_KEYS.inject({}){|o,k| o.merge!(k => send(k)) }
|
29
|
+
end
|
30
|
+
|
31
|
+
def reset
|
32
|
+
self.adapter = DEFAULT_ADAPTER
|
33
|
+
self.api_key = DEFAULT_API_KEY
|
34
|
+
self.endpoint = DEFAULT_ENDPOINT
|
35
|
+
self.format = DEFAULT_FORMAT
|
36
|
+
self.jurisdiction = DEFAULT_JURISDICTION
|
37
|
+
self.proxy = DEFAULT_PROXY
|
38
|
+
self.user_agent = DEFAULT_USER_AGENT
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
data/open311.gemspec
ADDED
@@ -0,0 +1,36 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
require File.expand_path("../lib/open311/version", __FILE__)
|
3
|
+
|
4
|
+
Gem::Specification.new do |s|
|
5
|
+
s.add_development_dependency("bundler", "~> 1.0")
|
6
|
+
s.add_development_dependency("libxml-ruby", "~> 1.1")
|
7
|
+
s.add_development_dependency("rake", "~> 0.8")
|
8
|
+
s.add_development_dependency("rcov", "~> 0.9")
|
9
|
+
s.add_development_dependency("rspec", "~> 2.0.1")
|
10
|
+
s.add_development_dependency("webmock", "~> 1.5")
|
11
|
+
s.add_development_dependency("yajl-ruby", "~> 0.7")
|
12
|
+
s.add_development_dependency("yard", "~> 0.6")
|
13
|
+
s.add_development_dependency("ZenTest", "~> 4.4")
|
14
|
+
s.add_runtime_dependency("hashie", "~> 0.4.0")
|
15
|
+
s.add_runtime_dependency("faraday", "~> 0.5.2")
|
16
|
+
s.add_runtime_dependency("faraday_middleware", "~> 0.2.3")
|
17
|
+
s.add_runtime_dependency("multi_json", "~> 0.0.5")
|
18
|
+
s.add_runtime_dependency("multi_xml", "~> 0.2.0")
|
19
|
+
s.authors = ["Dan Melton", "Erik Michaels-Ober"]
|
20
|
+
s.description = %q{A Ruby wrapper for the Open311 API v2.}
|
21
|
+
s.post_install_message =<<eos
|
22
|
+
Using this gem for your project or company? Add it to the apps wiki!
|
23
|
+
https://github.com/cfalabs/open311/wiki/apps
|
24
|
+
eos
|
25
|
+
s.email = ["dan@codeforamerica.org"]
|
26
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
|
27
|
+
s.files = `git ls-files`.split("\n")
|
28
|
+
s.homepage = "http://rubygems.org/gems/open311"
|
29
|
+
s.name = "open311"
|
30
|
+
s.platform = Gem::Platform::RUBY
|
31
|
+
s.require_paths = ["lib"]
|
32
|
+
s.required_rubygems_version = Gem::Requirement.new(">= 1.3.6") if s.respond_to? :required_rubygems_version=
|
33
|
+
s.summary = s.description
|
34
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
35
|
+
s.version = Open311::VERSION
|
36
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
<?xml version="1.0" encoding="utf-8"?>
|
2
|
+
<services xmlns:m="http://org/sfgov/sf311v2/services" xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"><service><service_code>001</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Litter Receptacles</group><service_name>Cans_Left_Out_24x7</service_name><description>Garbage or recycling cans that have been left out for more than 24 hours after collection. Violators will be cited.
|
3
|
+
</description></service><service><service_code>002</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Street Defects</group><service_name>Construction_Plate_Shifted</service_name><description>Metal construction plate covering the street or sidewalk has been moved.
|
4
|
+
</description></service><service><service_code>003</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sidewalk or Curb</group><service_name>Curb_or_Curb_Ramp_Defect</service_name><description>Sidewalk curb or ramp has problems such as cracking, missing pieces, holes, and/or chipped curb.
|
5
|
+
</description></service><service><service_code>004</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Litter Receptacles</group><service_name>Damaged_City_Can</service_name><description>Damage to a city garbage receptacle such as missing parts (lid, door, liner) or other physical damage.
|
6
|
+
</description></service><service><service_code>005</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sidewalk or Curb</group><service_name>Damaged_Side_Sewer_Vent_Cover</service_name><description>Damage to a side sewer vent cover with problems such as cracking, bending, rusting, or denting</description></service><service><service_code>006</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Tree Maintenance</group><service_name>Damaged_Tree</service_name><description>Damage to a city maintained tree. To check whether a tree is city maintained: http://bit.ly/6hsDk1</description></service><service><service_code>007</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Graffiti</group><service_name>Graffiti - Public - Bike_rack</service_name><description>Graffiti on a bike rack that does not contain racial slurs, profanity, or gang related language</description></service><service><service_code>008</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Graffiti</group><service_name>Graffiti - Public - News_rack</service_name><description>Graffiti on a news rack that does not contain racial slurs, profanity, or gang related language
|
7
|
+
</description></service><service><service_code>009</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Graffiti</group><service_name>Graffiti - Public - Parking_meter</service_name><description>Graffiti on a parking meter that does not contain racial slurs, profanity, or gang related language
|
8
|
+
</description></service><service><service_code>010</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Graffiti</group><service_name>Graffiti - Public - Pay_phone</service_name><description>Graffiti on a pay phone that does not contain racial slurs, profanity, or gang related language.
|
9
|
+
</description></service><service><service_code>011</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Graffiti</group><service_name>Graffiti - Private - Not_Offensive</service_name><description>Graffiti on a privately owned building or structure that does not contain racial slurs, profanity, or gang related language
|
10
|
+
</description></service><service><service_code>012</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Graffiti</group><service_name>Graffiti - Private - Offensive</service_name><description>Graffiti on a privately owned building or structure that contains racial slurs, profanity, or gang related language
|
11
|
+
</description></service><service><service_code>013</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Graffiti</group><service_name>Graffiti - Public - Other_enter_additional_details_below</service_name><description>Graffiti on public property (building, pole, sidewalk, hydrant, etc) with racial slurs, profanity, or gang related language
|
12
|
+
</description></service><service><service_code>015</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Illegal Dumping</group><service_name>Illegal_Dumping</service_name><description>Identify someone that has dumped or is dumping furniture or garbage onto the street or sidewalk. Violators will be cited
|
13
|
+
</description></service><service><service_code>016</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Tree Maintenance</group><service_name>Landscaping</service_name><description>Request maintenance on public property (except on park property) such as lawn mowing, bush or strip trimming and removal
|
14
|
+
</description></service><service><service_code>017</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Street and Sidewalk Cleaning</group><service_name>Missed_Route_Mechanical_Sweeping</service_name><description>Street cleaning sweeper did not show up as scheduled according to the street cleaning signs
|
15
|
+
</description></service><service><service_code>018</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sidewalk or Curb</group><service_name>Missing_Side_Sewer_Vent_Cover</service_name><description>The 4" side sewer vent cover (http://bit.ly/57BlOv) is missing from the sidewalk
|
16
|
+
</description></service><service><service_code>019</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Overflowing City Receptacle or Dumpster</group><service_name>Overflowing_City_Receptacle_or_Dumpster</service_name><description>City receptacle is overflowing and/or has garbage on and around the container
|
17
|
+
</description></service><service><service_code>020</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Tree Maintenance</group><service_name>Overgrown_Tree</service_name><description>Request that a city maintained tree (except on park property) be trimmed. To check whether a tree is city maintained: http://bit.ly/6hsDk1
|
18
|
+
</description></service><service><service_code>021</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Street Defects</group><service_name>Pavement_Defect</service_name><description>Defect on the street such as broken, cracked, and sinking asphalt or concrete
|
19
|
+
</description></service><service><service_code>022</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sewer Issues</group><service_name>Sewage_Back_Up Out_of_catch_basin</service_name><description>Sewage or dirty water coming out of a catchbasin (located at the corner of intersections)
|
20
|
+
</description></service><service><service_code>023</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sewer Issues</group><service_name>Side_Sewer_issues Water_coming_out</service_name><description>Sewage or odor coming out of a 4 inch side sewer (http://bit.ly/57BlOv) located on the sidewalk
|
21
|
+
</description></service><service><service_code>024</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sidewalk Cleaning</group><service_name>Sidewalk_Cleaning</service_name><description>Have garbage or human waste removed from the sidewalk and/or request services such as steam cleaning of sidewalks
|
22
|
+
</description></service><service><service_code>025</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sidewalk Defect</group><service_name>Sidewalk_Defect</service_name><description>Defect on the sidewalk such as broken, cracked, and/or sinking concrete
|
23
|
+
</description></service><service><service_code>026</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Street Cleaning</group><service_name>Street_Cleaning</service_name><description>Request to have garbage or human waste removed from the street
|
24
|
+
</description></service><service><service_code>027</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Tree Maintenance</group><service_name>Damaging_Property</service_name><description>Tree is damaging property (except for parks) or housing structure. City will address problem if it is a city maintained tree otherwise the property owner is notified to correct the issue
|
25
|
+
</description></service><service><service_code>028</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Graffiti</group><service_name>Water_Main_Break</service_name><description>Street is flooding due to water coming from within the asphalt or from a catchbasin
|
26
|
+
</description></service><service><service_code>029</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Graffiti</group><service_name>Sign - Defaced</service_name><description>Graffiti on a street sign such as a stop sign, street name, and/or other parking and traffic signs
|
27
|
+
</description></service><service><service_code>030</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sewer Issues</group><service_name>Side_Sewer_issues Odor</service_name><description>Odor coming out of a 4 inch side sewer (http://bit.ly/57BlOv) located on the sidewalk.
|
28
|
+
</description></service><service><service_code>031</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sewer Issues</group><service_name>Sewage_Back_up Out_of_manhole_cover</service_name><description>Sewage or dirty water coming out of a manhole cover (typically located in the a street or alley)
|
29
|
+
</description></service><service><service_code>032</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Sewer Issues</group><service_name>Sewage_Back_up Outofsewervent4inch</service_name><description>Sewage or dirty water coming out of a sewer vent (located on the sidewalk)
|
30
|
+
</description></service><service><service_code>375</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Street or Sidewalk</group><service_name>Damaged_Benches_on_Sidewalk</service_name><description>Report a damaged bench on city property.</description></service><service><service_code>376</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Street or Sidewalk</group><service_name>Damaged_Bike_Rack</service_name><description>Report a damaged bike rack on city property.</description></service><service><service_code>377</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Street or Sidewalk</group><service_name>Damaged_Kiosk_or_Public_Toilet</service_name><description>Report a damaged kiosk or public toilet on city property.</description></service><service><service_code>378</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Street or Sidewalk</group><service_name>Damaged_News_Rack</service_name><description>Report a damaged news rack on city property.</description></service><service><service_code>379</service_code><metadata>false</metadata><type>realtime</type><keywords/><group>Street or Sidewalk</group><service_name>Damaged_Parking_Meter</service_name><description>Report a damaged parking meter on city property.</description></service></services>
|
@@ -0,0 +1,27 @@
|
|
1
|
+
require File.expand_path('../spec_helper', __FILE__)
|
2
|
+
|
3
|
+
describe Open311, ".service_list" do
|
4
|
+
before do
|
5
|
+
Open311.configure do |config|
|
6
|
+
config.endpoint = 'https://open311.sfgov.org/'
|
7
|
+
config.format = 'xml'
|
8
|
+
config.jurisdiction = 'sfgov.org'
|
9
|
+
end
|
10
|
+
stub_request(:get, 'https://open311.sfgov.org/dev/v2/services.xml').
|
11
|
+
with(:query => {:jurisdiction_id => 'sfgov.org'}).
|
12
|
+
to_return(:body => fixture('services.xml'), :headers => {'Content-Type' => 'text/xml; charset=utf-8'})
|
13
|
+
end
|
14
|
+
|
15
|
+
it "should request the correct resource" do
|
16
|
+
Open311.service_list
|
17
|
+
a_request(:get, 'https://open311.sfgov.org/dev/v2/services.xml').
|
18
|
+
with(:query => {:jurisdiction_id => 'sfgov.org'}).
|
19
|
+
should have_been_made
|
20
|
+
end
|
21
|
+
|
22
|
+
it "should return the correct results" do
|
23
|
+
services = Open311.service_list
|
24
|
+
services.should be_an Array
|
25
|
+
services.first.service_code.should == '001'
|
26
|
+
end
|
27
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
require File.expand_path('../../lib/open311', __FILE__)
|
2
|
+
|
3
|
+
require 'webmock/rspec'
|
4
|
+
RSpec.configure do |config|
|
5
|
+
config.include WebMock::API
|
6
|
+
end
|
7
|
+
|
8
|
+
def fixture_path
|
9
|
+
File.expand_path("../fixtures", __FILE__)
|
10
|
+
end
|
11
|
+
|
12
|
+
def fixture(file)
|
13
|
+
File.new(fixture_path + '/' + file)
|
14
|
+
end
|
metadata
ADDED
@@ -0,0 +1,312 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: open311
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
hash: 31
|
5
|
+
prerelease: false
|
6
|
+
segments:
|
7
|
+
- 0
|
8
|
+
- 0
|
9
|
+
- 0
|
10
|
+
version: 0.0.0
|
11
|
+
platform: ruby
|
12
|
+
authors:
|
13
|
+
- Dan Melton
|
14
|
+
- Erik Michaels-Ober
|
15
|
+
autorequire:
|
16
|
+
bindir: bin
|
17
|
+
cert_chain: []
|
18
|
+
|
19
|
+
date: 2010-11-08 00:00:00 -08:00
|
20
|
+
default_executable:
|
21
|
+
dependencies:
|
22
|
+
- !ruby/object:Gem::Dependency
|
23
|
+
name: bundler
|
24
|
+
prerelease: false
|
25
|
+
requirement: &id001 !ruby/object:Gem::Requirement
|
26
|
+
none: false
|
27
|
+
requirements:
|
28
|
+
- - ~>
|
29
|
+
- !ruby/object:Gem::Version
|
30
|
+
hash: 15
|
31
|
+
segments:
|
32
|
+
- 1
|
33
|
+
- 0
|
34
|
+
version: "1.0"
|
35
|
+
type: :development
|
36
|
+
version_requirements: *id001
|
37
|
+
- !ruby/object:Gem::Dependency
|
38
|
+
name: libxml-ruby
|
39
|
+
prerelease: false
|
40
|
+
requirement: &id002 !ruby/object:Gem::Requirement
|
41
|
+
none: false
|
42
|
+
requirements:
|
43
|
+
- - ~>
|
44
|
+
- !ruby/object:Gem::Version
|
45
|
+
hash: 13
|
46
|
+
segments:
|
47
|
+
- 1
|
48
|
+
- 1
|
49
|
+
version: "1.1"
|
50
|
+
type: :development
|
51
|
+
version_requirements: *id002
|
52
|
+
- !ruby/object:Gem::Dependency
|
53
|
+
name: rake
|
54
|
+
prerelease: false
|
55
|
+
requirement: &id003 !ruby/object:Gem::Requirement
|
56
|
+
none: false
|
57
|
+
requirements:
|
58
|
+
- - ~>
|
59
|
+
- !ruby/object:Gem::Version
|
60
|
+
hash: 27
|
61
|
+
segments:
|
62
|
+
- 0
|
63
|
+
- 8
|
64
|
+
version: "0.8"
|
65
|
+
type: :development
|
66
|
+
version_requirements: *id003
|
67
|
+
- !ruby/object:Gem::Dependency
|
68
|
+
name: rcov
|
69
|
+
prerelease: false
|
70
|
+
requirement: &id004 !ruby/object:Gem::Requirement
|
71
|
+
none: false
|
72
|
+
requirements:
|
73
|
+
- - ~>
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
hash: 25
|
76
|
+
segments:
|
77
|
+
- 0
|
78
|
+
- 9
|
79
|
+
version: "0.9"
|
80
|
+
type: :development
|
81
|
+
version_requirements: *id004
|
82
|
+
- !ruby/object:Gem::Dependency
|
83
|
+
name: rspec
|
84
|
+
prerelease: false
|
85
|
+
requirement: &id005 !ruby/object:Gem::Requirement
|
86
|
+
none: false
|
87
|
+
requirements:
|
88
|
+
- - ~>
|
89
|
+
- !ruby/object:Gem::Version
|
90
|
+
hash: 13
|
91
|
+
segments:
|
92
|
+
- 2
|
93
|
+
- 0
|
94
|
+
- 1
|
95
|
+
version: 2.0.1
|
96
|
+
type: :development
|
97
|
+
version_requirements: *id005
|
98
|
+
- !ruby/object:Gem::Dependency
|
99
|
+
name: webmock
|
100
|
+
prerelease: false
|
101
|
+
requirement: &id006 !ruby/object:Gem::Requirement
|
102
|
+
none: false
|
103
|
+
requirements:
|
104
|
+
- - ~>
|
105
|
+
- !ruby/object:Gem::Version
|
106
|
+
hash: 5
|
107
|
+
segments:
|
108
|
+
- 1
|
109
|
+
- 5
|
110
|
+
version: "1.5"
|
111
|
+
type: :development
|
112
|
+
version_requirements: *id006
|
113
|
+
- !ruby/object:Gem::Dependency
|
114
|
+
name: yajl-ruby
|
115
|
+
prerelease: false
|
116
|
+
requirement: &id007 !ruby/object:Gem::Requirement
|
117
|
+
none: false
|
118
|
+
requirements:
|
119
|
+
- - ~>
|
120
|
+
- !ruby/object:Gem::Version
|
121
|
+
hash: 5
|
122
|
+
segments:
|
123
|
+
- 0
|
124
|
+
- 7
|
125
|
+
version: "0.7"
|
126
|
+
type: :development
|
127
|
+
version_requirements: *id007
|
128
|
+
- !ruby/object:Gem::Dependency
|
129
|
+
name: yard
|
130
|
+
prerelease: false
|
131
|
+
requirement: &id008 !ruby/object:Gem::Requirement
|
132
|
+
none: false
|
133
|
+
requirements:
|
134
|
+
- - ~>
|
135
|
+
- !ruby/object:Gem::Version
|
136
|
+
hash: 7
|
137
|
+
segments:
|
138
|
+
- 0
|
139
|
+
- 6
|
140
|
+
version: "0.6"
|
141
|
+
type: :development
|
142
|
+
version_requirements: *id008
|
143
|
+
- !ruby/object:Gem::Dependency
|
144
|
+
name: ZenTest
|
145
|
+
prerelease: false
|
146
|
+
requirement: &id009 !ruby/object:Gem::Requirement
|
147
|
+
none: false
|
148
|
+
requirements:
|
149
|
+
- - ~>
|
150
|
+
- !ruby/object:Gem::Version
|
151
|
+
hash: 19
|
152
|
+
segments:
|
153
|
+
- 4
|
154
|
+
- 4
|
155
|
+
version: "4.4"
|
156
|
+
type: :development
|
157
|
+
version_requirements: *id009
|
158
|
+
- !ruby/object:Gem::Dependency
|
159
|
+
name: hashie
|
160
|
+
prerelease: false
|
161
|
+
requirement: &id010 !ruby/object:Gem::Requirement
|
162
|
+
none: false
|
163
|
+
requirements:
|
164
|
+
- - ~>
|
165
|
+
- !ruby/object:Gem::Version
|
166
|
+
hash: 15
|
167
|
+
segments:
|
168
|
+
- 0
|
169
|
+
- 4
|
170
|
+
- 0
|
171
|
+
version: 0.4.0
|
172
|
+
type: :runtime
|
173
|
+
version_requirements: *id010
|
174
|
+
- !ruby/object:Gem::Dependency
|
175
|
+
name: faraday
|
176
|
+
prerelease: false
|
177
|
+
requirement: &id011 !ruby/object:Gem::Requirement
|
178
|
+
none: false
|
179
|
+
requirements:
|
180
|
+
- - ~>
|
181
|
+
- !ruby/object:Gem::Version
|
182
|
+
hash: 15
|
183
|
+
segments:
|
184
|
+
- 0
|
185
|
+
- 5
|
186
|
+
- 2
|
187
|
+
version: 0.5.2
|
188
|
+
type: :runtime
|
189
|
+
version_requirements: *id011
|
190
|
+
- !ruby/object:Gem::Dependency
|
191
|
+
name: faraday_middleware
|
192
|
+
prerelease: false
|
193
|
+
requirement: &id012 !ruby/object:Gem::Requirement
|
194
|
+
none: false
|
195
|
+
requirements:
|
196
|
+
- - ~>
|
197
|
+
- !ruby/object:Gem::Version
|
198
|
+
hash: 17
|
199
|
+
segments:
|
200
|
+
- 0
|
201
|
+
- 2
|
202
|
+
- 3
|
203
|
+
version: 0.2.3
|
204
|
+
type: :runtime
|
205
|
+
version_requirements: *id012
|
206
|
+
- !ruby/object:Gem::Dependency
|
207
|
+
name: multi_json
|
208
|
+
prerelease: false
|
209
|
+
requirement: &id013 !ruby/object:Gem::Requirement
|
210
|
+
none: false
|
211
|
+
requirements:
|
212
|
+
- - ~>
|
213
|
+
- !ruby/object:Gem::Version
|
214
|
+
hash: 21
|
215
|
+
segments:
|
216
|
+
- 0
|
217
|
+
- 0
|
218
|
+
- 5
|
219
|
+
version: 0.0.5
|
220
|
+
type: :runtime
|
221
|
+
version_requirements: *id013
|
222
|
+
- !ruby/object:Gem::Dependency
|
223
|
+
name: multi_xml
|
224
|
+
prerelease: false
|
225
|
+
requirement: &id014 !ruby/object:Gem::Requirement
|
226
|
+
none: false
|
227
|
+
requirements:
|
228
|
+
- - ~>
|
229
|
+
- !ruby/object:Gem::Version
|
230
|
+
hash: 23
|
231
|
+
segments:
|
232
|
+
- 0
|
233
|
+
- 2
|
234
|
+
- 0
|
235
|
+
version: 0.2.0
|
236
|
+
type: :runtime
|
237
|
+
version_requirements: *id014
|
238
|
+
description: A Ruby wrapper for the Open311 API v2.
|
239
|
+
email:
|
240
|
+
- dan@codeforamerica.org
|
241
|
+
executables: []
|
242
|
+
|
243
|
+
extensions: []
|
244
|
+
|
245
|
+
extra_rdoc_files: []
|
246
|
+
|
247
|
+
files:
|
248
|
+
- .gitignore
|
249
|
+
- .rspec
|
250
|
+
- .yardopts
|
251
|
+
- Gemfile
|
252
|
+
- Gemfile.lock
|
253
|
+
- LICENSE.mkd
|
254
|
+
- README.mkd
|
255
|
+
- Rakefile
|
256
|
+
- autotest/discover.rb
|
257
|
+
- lib/faraday/multipart.rb
|
258
|
+
- lib/faraday/raise_error.rb
|
259
|
+
- lib/open311.rb
|
260
|
+
- lib/open311/client.rb
|
261
|
+
- lib/open311/client/connection.rb
|
262
|
+
- lib/open311/client/request.rb
|
263
|
+
- lib/open311/client/service.rb
|
264
|
+
- lib/open311/configuration.rb
|
265
|
+
- lib/open311/version.rb
|
266
|
+
- open311.gemspec
|
267
|
+
- spec/fixtures/services.xml
|
268
|
+
- spec/open311_spec.rb
|
269
|
+
- spec/spec_helper.rb
|
270
|
+
has_rdoc: true
|
271
|
+
homepage: http://rubygems.org/gems/open311
|
272
|
+
licenses: []
|
273
|
+
|
274
|
+
post_install_message: |
|
275
|
+
Using this gem for your project or company? Add it to the apps wiki!
|
276
|
+
https://github.com/cfalabs/open311/wiki/apps
|
277
|
+
|
278
|
+
rdoc_options: []
|
279
|
+
|
280
|
+
require_paths:
|
281
|
+
- lib
|
282
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
283
|
+
none: false
|
284
|
+
requirements:
|
285
|
+
- - ">="
|
286
|
+
- !ruby/object:Gem::Version
|
287
|
+
hash: 3
|
288
|
+
segments:
|
289
|
+
- 0
|
290
|
+
version: "0"
|
291
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
292
|
+
none: false
|
293
|
+
requirements:
|
294
|
+
- - ">="
|
295
|
+
- !ruby/object:Gem::Version
|
296
|
+
hash: 23
|
297
|
+
segments:
|
298
|
+
- 1
|
299
|
+
- 3
|
300
|
+
- 6
|
301
|
+
version: 1.3.6
|
302
|
+
requirements: []
|
303
|
+
|
304
|
+
rubyforge_project:
|
305
|
+
rubygems_version: 1.3.7
|
306
|
+
signing_key:
|
307
|
+
specification_version: 3
|
308
|
+
summary: A Ruby wrapper for the Open311 API v2.
|
309
|
+
test_files:
|
310
|
+
- spec/fixtures/services.xml
|
311
|
+
- spec/open311_spec.rb
|
312
|
+
- spec/spec_helper.rb
|