lelylan-rb 0.0.1
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 +26 -0
- data/CHANGELOG.md +5 -0
- data/Gemfile +7 -0
- data/Guardfile +5 -0
- data/LICENSE.md +1 -0
- data/README.md +218 -0
- data/Rakefile +21 -0
- data/lelylan_rb.gemspec +36 -0
- data/lib/faraday/response/raise_http_error.rb +35 -0
- data/lib/lelylan.rb +26 -0
- data/lib/lelylan/authentication.rb +11 -0
- data/lib/lelylan/client.rb +47 -0
- data/lib/lelylan/client/categories.rb +112 -0
- data/lib/lelylan/client/consumptions.rb +93 -0
- data/lib/lelylan/client/devices.rb +211 -0
- data/lib/lelylan/client/functions.rb +118 -0
- data/lib/lelylan/client/histories.rb +42 -0
- data/lib/lelylan/client/locations.rb +92 -0
- data/lib/lelylan/client/properties.rb +115 -0
- data/lib/lelylan/client/statuses.rb +110 -0
- data/lib/lelylan/client/types.rb +109 -0
- data/lib/lelylan/configuration.rb +65 -0
- data/lib/lelylan/connection.rb +33 -0
- data/lib/lelylan/error.rb +34 -0
- data/lib/lelylan/request.rb +70 -0
- data/lib/lelylan/version.rb +15 -0
- data/spec/faraday/response_spec.rb +37 -0
- data/spec/fixtures/categories.json +7 -0
- data/spec/fixtures/category.json +7 -0
- data/spec/fixtures/consumption.json +11 -0
- data/spec/fixtures/consumptions.json +11 -0
- data/spec/fixtures/device.json +25 -0
- data/spec/fixtures/devices.json +25 -0
- data/spec/fixtures/function.json +15 -0
- data/spec/fixtures/functions.json +15 -0
- data/spec/fixtures/histories.json +16 -0
- data/spec/fixtures/history.json +16 -0
- data/spec/fixtures/location.json +55 -0
- data/spec/fixtures/locations.json +18 -0
- data/spec/fixtures/oauth2/refresh.json +6 -0
- data/spec/fixtures/oauth2/token.json +6 -0
- data/spec/fixtures/pending.json +12 -0
- data/spec/fixtures/properties.json +9 -0
- data/spec/fixtures/property.json +9 -0
- data/spec/fixtures/status.json +24 -0
- data/spec/fixtures/statuses.json +24 -0
- data/spec/fixtures/type.json +94 -0
- data/spec/fixtures/types.json +88 -0
- data/spec/helper.rb +71 -0
- data/spec/lelylan/client/categories_spec.rb +178 -0
- data/spec/lelylan/client/consumptions_spec.rb +150 -0
- data/spec/lelylan/client/devices_spec.rb +342 -0
- data/spec/lelylan/client/functions_spec.rb +184 -0
- data/spec/lelylan/client/histories_spec.rb +64 -0
- data/spec/lelylan/client/locations_spec.rb +155 -0
- data/spec/lelylan/client/properties_spec.rb +184 -0
- data/spec/lelylan/client/statuses_spec.rb +184 -0
- data/spec/lelylan/client/types_spec.rb +184 -0
- data/spec/lelylan/client_spec.rb +32 -0
- data/spec/lelylan/oauth2_spec.rb +54 -0
- data/spec/lelylan_spec.rb +32 -0
- metadata +351 -0
data/.gitignore
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
*.gem
|
2
|
+
*.rbc
|
3
|
+
*.swp
|
4
|
+
*.tmproj
|
5
|
+
*.DS_Store
|
6
|
+
*~
|
7
|
+
.\#*
|
8
|
+
.bundle
|
9
|
+
.config
|
10
|
+
.yardoc
|
11
|
+
.yardopts
|
12
|
+
.rvmrc
|
13
|
+
Gemfile.lock
|
14
|
+
InstalledFiles
|
15
|
+
\#*
|
16
|
+
_yardoc
|
17
|
+
coverage
|
18
|
+
doc/
|
19
|
+
lib/bundler/man
|
20
|
+
pkg
|
21
|
+
rdoc
|
22
|
+
spec/reports
|
23
|
+
test/tmp
|
24
|
+
test/version_tmp
|
25
|
+
tmp
|
26
|
+
tmtags
|
data/CHANGELOG.md
ADDED
data/Gemfile
ADDED
data/Guardfile
ADDED
data/LICENSE.md
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
Copyright (c) 2013 Lelylan
|
data/README.md
ADDED
@@ -0,0 +1,218 @@
|
|
1
|
+
# Lelylan Ruby Gem
|
2
|
+
|
3
|
+
Ruby client library for [Lelylan API](http://dev.lelylan.com)
|
4
|
+
|
5
|
+
|
6
|
+
## Requirements
|
7
|
+
|
8
|
+
Ruby client library is tested against MRI 1.9.3.
|
9
|
+
|
10
|
+
|
11
|
+
## Installation
|
12
|
+
|
13
|
+
Install gem using Bundler.
|
14
|
+
|
15
|
+
gem 'lelylan-rb', require: 'lelylan'
|
16
|
+
|
17
|
+
Development version.
|
18
|
+
|
19
|
+
gem 'lelylan-rb', require: 'lelylan', git: 'https://github.com/lelylan/lelylan-rb', branch: 'dev'
|
20
|
+
|
21
|
+
|
22
|
+
## Resources
|
23
|
+
|
24
|
+
* [Ruby gem documentation](http://rdoc.info/gems/lelylan-rb)
|
25
|
+
* [Lelylan API](http://dev.lelylan.com)
|
26
|
+
|
27
|
+
|
28
|
+
## Getting started
|
29
|
+
|
30
|
+
Require gems.
|
31
|
+
|
32
|
+
require 'rubygems'
|
33
|
+
require 'lelylan-rb'
|
34
|
+
|
35
|
+
|
36
|
+
### Create the access token
|
37
|
+
|
38
|
+
Create a client (uses the [OAuth2 gem](https://github.com/intridea/oauth2/)).
|
39
|
+
|
40
|
+
oauth = OAuth2::Client.new(client_id, client_secret, site: site)
|
41
|
+
|
42
|
+
Redirect the application to the Lelylan authorization page.
|
43
|
+
|
44
|
+
redirect oauth.auth_code.authorize_url(redirect_uri: redirect_uri)
|
45
|
+
|
46
|
+
Create the access token. The params[:code] contains the authorization
|
47
|
+
code created from Lelylan and sent to the redirect_uri.
|
48
|
+
|
49
|
+
token = oauth.auth_code.get_token(params[:code], redirect_uri: redirect_uri)
|
50
|
+
|
51
|
+
### Create the Lelylan client.
|
52
|
+
|
53
|
+
client = Lelylan::Client.new(token: token)
|
54
|
+
|
55
|
+
### Access Lelylan API
|
56
|
+
|
57
|
+
Get 10 devices.
|
58
|
+
|
59
|
+
client.devices(per: 10)
|
60
|
+
|
61
|
+
Get a device based on its URI.
|
62
|
+
|
63
|
+
client.device('http://api.lelylan.com/devices/:id')
|
64
|
+
|
65
|
+
Search a device based on its name.
|
66
|
+
|
67
|
+
client.devices(name: 'Dimmer').first
|
68
|
+
|
69
|
+
Create a device (in this case we suppose the type is a dimmer)
|
70
|
+
|
71
|
+
device = client.create_device(name: 'Closet dimmer', type_uri: dimmer.uri)
|
72
|
+
|
73
|
+
Execute a function.
|
74
|
+
|
75
|
+
client.execute(device.uri, function.uri)
|
76
|
+
|
77
|
+
Get a public type based on its URI. Remember, when a resource is public the client
|
78
|
+
with a token is not needed.
|
79
|
+
|
80
|
+
Lelylan.type('http://api.lelylan.com/types/:id')
|
81
|
+
|
82
|
+
|
83
|
+
## More examples
|
84
|
+
|
85
|
+
For more examples check out the [ruby gem documentation](http://rdoc.info/gems/lelylan-rb).
|
86
|
+
|
87
|
+
* [Device examples](docs/Lelylan/Client/Devices)
|
88
|
+
* [Consumption examples](docs/Lelylan/Client/Consumptions)
|
89
|
+
* [Hisotry examples](docs/Lelylan/Client/Histories)
|
90
|
+
* [Types examples](docs/Lelylan/Client/Types)
|
91
|
+
* [Properties examples](docs/Lelylan/Client/Properties)
|
92
|
+
* [Functions examples](docs/Lelylan/Client/Functions)
|
93
|
+
* [Statuses examples](docs/Lelylan/Client/Statuses)
|
94
|
+
* [Categories examples](docs/Lelylan/Client/Categories)
|
95
|
+
* [Locations examples](docs/Lelylan/Client/Locations)
|
96
|
+
|
97
|
+
## Authorization flows
|
98
|
+
|
99
|
+
Lelylan support four OAuth2 authorization flows.
|
100
|
+
|
101
|
+
### Authorization code flows
|
102
|
+
|
103
|
+
oauth = OAuth2::Client.new(client_id, client_secret, site: site)
|
104
|
+
redirect oauth.auth_code.authorize_url(redirect_uri: redirect_uri)
|
105
|
+
token = oauth.auth_code.get_token(params[:code], redirect_uri: redirect_uri)
|
106
|
+
|
107
|
+
### Implicit grant flow
|
108
|
+
|
109
|
+
oauth = OAuth2::Client.new(client_id, client_secret, site: site)
|
110
|
+
redirect oauth.auth_code.authorize_url(redirect_uri: redirect_uri)
|
111
|
+
token = OAuth2::AccessToken.from_kvform(client, params)
|
112
|
+
|
113
|
+
### Resource owner password credentials flow
|
114
|
+
|
115
|
+
oauth = OAuth2::Client.new(client_id, client_secret, site: site)
|
116
|
+
token = oauth.password.get_token('email', 'password')
|
117
|
+
|
118
|
+
### Client credentials flow
|
119
|
+
|
120
|
+
token = oauth.client_credentials.get_token
|
121
|
+
|
122
|
+
All access tokens, when expired, are automatically refreshed.
|
123
|
+
|
124
|
+
|
125
|
+
## Settings
|
126
|
+
|
127
|
+
### API endpoint
|
128
|
+
|
129
|
+
Configuration block.
|
130
|
+
|
131
|
+
Lelylan.configure { |c| c.endpoint = 'https://lelylan.yourhouse.com' }
|
132
|
+
@client = Lelylan::Client.new(token: token)
|
133
|
+
|
134
|
+
Client instance.
|
135
|
+
|
136
|
+
@client = Lelylan::Client.new(token: token)
|
137
|
+
@client.endpoint = 'https://lelylan.yourhouse.com'
|
138
|
+
|
139
|
+
|
140
|
+
## Errors
|
141
|
+
|
142
|
+
Exceptions are raised when a 4xx or 5xx status code is returned.
|
143
|
+
|
144
|
+
Lelylan::BadRequest # 400
|
145
|
+
Lelylan::Unauthorized # 401
|
146
|
+
Lelylan::NotFound # 404
|
147
|
+
Lelylan::NotValid # 422
|
148
|
+
Lelylan::InternalServerError # 500
|
149
|
+
Lelylan::BadGateway # 502
|
150
|
+
Lelylan::ServiceUnavailable # 503
|
151
|
+
|
152
|
+
|
153
|
+
Through the error message attribute you can access the error information.
|
154
|
+
|
155
|
+
begin
|
156
|
+
@type = Lelylan::Type.type("https://type.lelylan.com/types/not_existing_uri")
|
157
|
+
rescue Lelylan::NotFound => e
|
158
|
+
puts "The resource #{e.message.error.uri} was not found"
|
159
|
+
end
|
160
|
+
|
161
|
+
Learn more about the [error response structure](http://dev.lelylan.com/rest/core/#errors).
|
162
|
+
|
163
|
+
|
164
|
+
## Contributing
|
165
|
+
|
166
|
+
Fork the repo on github and send a pull requests with topic branches. Do not forget to
|
167
|
+
provide specs to your contribution.
|
168
|
+
|
169
|
+
|
170
|
+
### Running specs
|
171
|
+
|
172
|
+
* Fork and clone the repository.
|
173
|
+
* Run `gem install bundler` to get the latest for the gemset.
|
174
|
+
* Run `bundle install` for dependencies.
|
175
|
+
* Run `bundle exec guard` and press enter to execute all specs.
|
176
|
+
|
177
|
+
|
178
|
+
## Spec guidelines
|
179
|
+
|
180
|
+
Follow [rspec best practices](https://docs.google.com/document/d/1gi00-wwPaLk5VvoAJhBVNh9Htw4Rwmj-Ut88T4M2MwI/edit?hl=en#) guidelines.
|
181
|
+
|
182
|
+
|
183
|
+
## Coding guidelines
|
184
|
+
|
185
|
+
Follow [github](https://github.com/styleguide/) guidelines.
|
186
|
+
|
187
|
+
|
188
|
+
## Feedback
|
189
|
+
|
190
|
+
Use the [issue tracker](http://github.com/lelylan/lelylan-rb/issues) for bugs.
|
191
|
+
[Mail](mailto:touch@lelylan.com) or [Tweet](http://twitter.com/lelylan) us for any idea that can improve the project.
|
192
|
+
|
193
|
+
|
194
|
+
## Links
|
195
|
+
|
196
|
+
* [GIT Repository](http://github.com/lelylan/lelylan-rb)
|
197
|
+
* [Lelylan Dev Center](http://dev.lelylan.com)
|
198
|
+
* [Lelylan Site](http://lelylan.com)
|
199
|
+
|
200
|
+
|
201
|
+
## Authors
|
202
|
+
|
203
|
+
[Andrea Reginato](http://twitter.com/andreareginato)
|
204
|
+
|
205
|
+
|
206
|
+
## Contributors
|
207
|
+
|
208
|
+
Special thanks to the following people for submitting patches.
|
209
|
+
|
210
|
+
|
211
|
+
## Changelog
|
212
|
+
|
213
|
+
See [CHANGELOG](people/blob/master/CHANGELOG.md)
|
214
|
+
|
215
|
+
|
216
|
+
## Copyright
|
217
|
+
|
218
|
+
Copyright (c) 2013 [Lelylan](http://lelylan.com). See [LICENSE](people/blob/master/LICENSE.md) for details.
|
data/Rakefile
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
require 'bundler'
|
2
|
+
Bundler::GemHelper.install_tasks
|
3
|
+
|
4
|
+
require 'rspec/core/rake_task'
|
5
|
+
RSpec::Core::RakeTask.new(:spec)
|
6
|
+
|
7
|
+
task :test => :spec
|
8
|
+
task :default => :spec
|
9
|
+
|
10
|
+
namespace :doc do
|
11
|
+
require 'yard'
|
12
|
+
YARD::Rake::YardocTask.new do |task|
|
13
|
+
task.files = ['README.md', 'CHANGELOG.md', 'lib/lelylan/client/**/*.rb']
|
14
|
+
task.options = [
|
15
|
+
'--plugin', 'yard-tomdoc',
|
16
|
+
'--markup-provider', 'redcarpet',
|
17
|
+
'--markup', 'markdown',
|
18
|
+
'--output-dir', 'doc'
|
19
|
+
]
|
20
|
+
end
|
21
|
+
end
|
data/lelylan_rb.gemspec
ADDED
@@ -0,0 +1,36 @@
|
|
1
|
+
# encoding: utf-8
|
2
|
+
require File.expand_path('../lib/lelylan/version', __FILE__)
|
3
|
+
|
4
|
+
Gem::Specification.new do |gem|
|
5
|
+
gem.add_dependency 'addressable', '~> 2.2'
|
6
|
+
gem.add_dependency 'oauth2', '~> 0.8'
|
7
|
+
gem.add_dependency 'faraday', '~> 0.8'
|
8
|
+
gem.add_dependency 'faraday_middleware', '~> 0.8'
|
9
|
+
gem.add_dependency 'hashie', '~> 1.2'
|
10
|
+
gem.add_dependency 'multi_json', '~> 1.3'
|
11
|
+
gem.add_development_dependency 'json'
|
12
|
+
gem.add_development_dependency 'maruku'
|
13
|
+
gem.add_development_dependency 'rake'
|
14
|
+
gem.add_development_dependency 'rspec'
|
15
|
+
gem.add_development_dependency 'simplecov'
|
16
|
+
gem.add_development_dependency 'webmock'
|
17
|
+
gem.add_development_dependency 'guard-rspec'
|
18
|
+
gem.add_development_dependency 'fuubar'
|
19
|
+
gem.add_development_dependency 'growl'
|
20
|
+
gem.add_development_dependency 'yard'
|
21
|
+
gem.add_development_dependency 'yard-tomdoc'
|
22
|
+
gem.add_development_dependency 'redcarpet'
|
23
|
+
gem.add_development_dependency 'github-markup'
|
24
|
+
gem.authors = ["Andrea Reginato"]
|
25
|
+
gem.description = %q{Ruby wrapper for Lelylan API}
|
26
|
+
gem.email = ['touch@lelylan.com']
|
27
|
+
gem.files = `git ls-files`.split("\n")
|
28
|
+
gem.homepage = 'https://github.com/lelylan/lelylan-rb'
|
29
|
+
gem.name = 'lelylan-rb'
|
30
|
+
gem.platform = Gem::Platform::RUBY
|
31
|
+
gem.require_paths = ['lib']
|
32
|
+
gem.required_rubygems_version = Gem::Requirement.new('>= 1.3.6')
|
33
|
+
gem.summary = gem.description
|
34
|
+
gem.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
35
|
+
gem.version = Lelylan::Version
|
36
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
require 'faraday'
|
2
|
+
require 'multi_json'
|
3
|
+
|
4
|
+
module Faraday
|
5
|
+
class Response::RaiseHttpError < Response::Middleware
|
6
|
+
def on_complete(response)
|
7
|
+
case response[:status].to_i
|
8
|
+
when 400
|
9
|
+
raise Lelylan::BadRequest, error_message(response)
|
10
|
+
when 401
|
11
|
+
raise Lelylan::Unauthorized, error_message(response)
|
12
|
+
when 403
|
13
|
+
raise Lelylan::Forbidden, error_message(response)
|
14
|
+
when 404
|
15
|
+
raise Lelylan::NotFound, error_message(response)
|
16
|
+
when 406
|
17
|
+
raise Lelylan::NotAcceptable, error_message(response)
|
18
|
+
when 422
|
19
|
+
raise Lelylan::UnprocessableEntity, error_message(response)
|
20
|
+
when 500
|
21
|
+
raise Lelylan::InternalServerError, error_message(response)
|
22
|
+
when 501
|
23
|
+
raise Lelylan::NotImplemented, error_message(response)
|
24
|
+
when 502
|
25
|
+
raise Lelylan::BadGateway, error_message(response)
|
26
|
+
when 503
|
27
|
+
raise Lelylan::ServiceUnavailable, error_message(response)
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
def error_message(response)
|
32
|
+
response[:body]
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
data/lib/lelylan.rb
ADDED
@@ -0,0 +1,26 @@
|
|
1
|
+
require 'lelylan/configuration'
|
2
|
+
require 'lelylan/client'
|
3
|
+
require 'lelylan/error'
|
4
|
+
require 'oauth2'
|
5
|
+
|
6
|
+
module Lelylan
|
7
|
+
extend Configuration
|
8
|
+
|
9
|
+
class << self
|
10
|
+
|
11
|
+
# Alias for Lelylan::Client.new
|
12
|
+
def new(options={})
|
13
|
+
Lelylan::Client.new(options)
|
14
|
+
end
|
15
|
+
|
16
|
+
# Delegate to Lelylan::Client.new
|
17
|
+
def method_missing(method, *args, &block)
|
18
|
+
return super unless new.respond_to?(method)
|
19
|
+
new.send(method, *args, &block)
|
20
|
+
end
|
21
|
+
|
22
|
+
def respond_to?(method, include_private=false)
|
23
|
+
new.respond_to?(method, include_private) || super(method, include_private)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
require 'lelylan/authentication'
|
2
|
+
require 'lelylan/connection'
|
3
|
+
require 'lelylan/request'
|
4
|
+
|
5
|
+
require 'lelylan/client/devices'
|
6
|
+
require 'lelylan/client/consumptions'
|
7
|
+
require 'lelylan/client/histories'
|
8
|
+
require 'lelylan/client/types'
|
9
|
+
require 'lelylan/client/properties'
|
10
|
+
require 'lelylan/client/functions'
|
11
|
+
require 'lelylan/client/statuses'
|
12
|
+
require 'lelylan/client/categories'
|
13
|
+
require 'lelylan/client/locations'
|
14
|
+
|
15
|
+
module Lelylan
|
16
|
+
class Client
|
17
|
+
attr_accessor(*Configuration::VALID_OPTIONS_KEYS)
|
18
|
+
|
19
|
+
def initialize(options={})
|
20
|
+
options = Lelylan.options.merge(options)
|
21
|
+
Configuration::VALID_OPTIONS_KEYS.each do |key|
|
22
|
+
send("#{key}=", options[key])
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
# helper method
|
27
|
+
def find_id(uri)
|
28
|
+
Addressable::URI.parse(uri).basename
|
29
|
+
end
|
30
|
+
|
31
|
+
# structure related
|
32
|
+
include Lelylan::Authentication
|
33
|
+
include Lelylan::Connection
|
34
|
+
include Lelylan::Request
|
35
|
+
|
36
|
+
# client related
|
37
|
+
include Lelylan::Client::Devices
|
38
|
+
include Lelylan::Client::Consumptions
|
39
|
+
include Lelylan::Client::Histories
|
40
|
+
include Lelylan::Client::Types
|
41
|
+
include Lelylan::Client::Properties
|
42
|
+
include Lelylan::Client::Functions
|
43
|
+
include Lelylan::Client::Statuses
|
44
|
+
include Lelylan::Client::Categories
|
45
|
+
include Lelylan::Client::Locations
|
46
|
+
end
|
47
|
+
end
|