xbmc-jsonrpc 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
data/.document ADDED
@@ -0,0 +1,5 @@
1
+ README.rdoc
2
+ lib/**/*.rb
3
+ bin/*
4
+ features/**/*.feature
5
+ LICENSE
data/.gitignore ADDED
@@ -0,0 +1,21 @@
1
+ ## MAC OS
2
+ .DS_Store
3
+
4
+ ## TEXTMATE
5
+ *.tmproj
6
+ tmtags
7
+
8
+ ## EMACS
9
+ *~
10
+ \#*
11
+ .\#*
12
+
13
+ ## VIM
14
+ *.swp
15
+
16
+ ## PROJECT::GENERAL
17
+ coverage
18
+ rdoc
19
+ pkg
20
+
21
+ ## PROJECT::SPECIFIC
data/LICENSE ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2009 atom smith
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.rdoc ADDED
@@ -0,0 +1,91 @@
1
+ = xbmc-jsonrpc
2
+
3
+ XBMC_JSONRPC is a module created for simple interaction with the XBMC JSONRPC API introduced in XBMC dharma 2.
4
+
5
+ Create a new connection:
6
+ irb(main):001:0> x = XBMC_JSONRPC.new
7
+ => XBMC_JSONRPC
8
+
9
+ List all commands (including the details):
10
+
11
+ irb(main):002:0> x.commands
12
+ => {"System.GetInfoLabels"=>{"executable"=>true, "permission"=>"ReadData", "description"=>"Retrieve info labels about the system"}, "Files.Download"=>{"executable"=>true, "permission"=>"ReadData", "description"=>"Specify a file to download to get info about how to download it, i.e a proper URL"}, "PicturePlayer.PlayPause"=>{"executable"=>true, "permission"=>"ControlPlayback", "description"=>"Pauses or unpause slideshow"}.....
13
+
14
+ Find suitable commands based on name / description:
15
+
16
+ irb(main):003:0> x.apropos :slideshow
17
+
18
+ PicturePlayer.PlayPause
19
+ Pauses or unpause slideshow
20
+
21
+
22
+ XBMC.StartSlideshow
23
+ Starts slideshow. Parameter example {"directory": "/foo/", "random": true, "recursive": true} or just string to recursively and random run directory
24
+
25
+
26
+ PicturePlayer.Stop
27
+ Stops slideshow
28
+
29
+
30
+ PicturePlayer.SkipNext
31
+ Skips to next picture in the slideshow
32
+
33
+
34
+ PicturePlayer.SkipPrevious
35
+ Skips to previous picture in the slideshow
36
+
37
+ => nil
38
+
39
+
40
+ Get the commands for a namespace:
41
+
42
+ irb(main):007:0> x::XBMC.commands
43
+
44
+ XBMC.Play
45
+ Starts playback
46
+
47
+
48
+ XBMC.GetVolume
49
+ Retrieve the current volume
50
+
51
+
52
+ XBMC.StartSlideshow
53
+ Starts slideshow. Parameter example {"directory": "/foo/", "random": true, "recursive": true} or just string to recursively and random run directory
54
+
55
+
56
+ XBMC.SetVolume
57
+ Set volume. Parameter integer between 0 amd 100
58
+
59
+
60
+ XBMC.Quit
61
+ Quit xbmc
62
+
63
+
64
+ XBMC.Log
65
+ Logs a line in the xbmc.log. Parameter example {"message": "foo", "level": "info"} or just a string to log message with level debug
66
+
67
+
68
+ XBMC.ToggleMute
69
+ Toggle mute
70
+
71
+ => [nil, nil, nil, nil, nil, nil, nil]
72
+
73
+
74
+ Commands are run like so:
75
+
76
+ irb(main):008:0> x::VideoPlayer.PlayPause
77
+ => {"result"=>{"playing"=>true, "paused"=>false}, "id"=>1, "jsonrpc"=>"2.0"}
78
+
79
+ == Note on Patches/Pull Requests
80
+
81
+ * Fork the project.
82
+ * Make your feature addition or bug fix.
83
+ * Add tests for it. This is important so I don't break it in a
84
+ future version unintentionally.
85
+ * Commit, do not mess with rakefile, version, or history.
86
+ (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
87
+ * Send me a pull request. Bonus points for topic branches.
88
+
89
+ == Copyright
90
+
91
+ Copyright (c) 2010 atom smith. See LICENSE for details.
data/Rakefile ADDED
@@ -0,0 +1,53 @@
1
+ require 'rubygems'
2
+ require 'rake'
3
+
4
+ begin
5
+ require 'jeweler'
6
+ Jeweler::Tasks.new do |gem|
7
+ gem.name = "xbmc-jsonrpc"
8
+ gem.summary = %Q{A module for interacting with xbmc's json-rpc server}
9
+ gem.description = %Q{A module for interacting with xbmc's json-rpc server}
10
+ gem.email = "re5etsmyth@gmail.com"
11
+ gem.homepage = "http://github.com/re5et/xbmc-jsonrpc"
12
+ gem.authors = ["atom smith"]
13
+ gem.add_development_dependency "thoughtbot-shoulda", ">= 0"
14
+ # gem is a Gem::Specification... see http://www.rubygems.org/read/chapter/20 for additional settings
15
+ end
16
+ Jeweler::GemcutterTasks.new
17
+ rescue LoadError
18
+ puts "Jeweler (or a dependency) not available. Install it with: gem install jeweler"
19
+ end
20
+
21
+ require 'rake/testtask'
22
+ Rake::TestTask.new(:test) do |test|
23
+ test.libs << 'lib' << 'test'
24
+ test.pattern = 'test/**/test_*.rb'
25
+ test.verbose = true
26
+ end
27
+
28
+ begin
29
+ require 'rcov/rcovtask'
30
+ Rcov::RcovTask.new do |test|
31
+ test.libs << 'test'
32
+ test.pattern = 'test/**/test_*.rb'
33
+ test.verbose = true
34
+ end
35
+ rescue LoadError
36
+ task :rcov do
37
+ abort "RCov is not available. In order to run rcov, you must: sudo gem install spicycode-rcov"
38
+ end
39
+ end
40
+
41
+ task :test => :check_dependencies
42
+
43
+ task :default => :test
44
+
45
+ require 'rake/rdoctask'
46
+ Rake::RDocTask.new do |rdoc|
47
+ version = File.exist?('VERSION') ? File.read('VERSION') : ""
48
+
49
+ rdoc.rdoc_dir = 'rdoc'
50
+ rdoc.title = "xbmc-jsonrpc #{version}"
51
+ rdoc.rdoc_files.include('README*')
52
+ rdoc.rdoc_files.include('lib/**/*.rb')
53
+ end
data/VERSION ADDED
@@ -0,0 +1 @@
1
+ 0.2.0
@@ -0,0 +1,457 @@
1
+ # This program allows easy interaction with XBMC's json-rpc API.
2
+ # Connection information is provided, and connection is created
3
+ # and stored for repeated use. The list of classes and methods
4
+ # available are retrieved from the XBMC json-rpc API, and can be
5
+ # accessed or referenced using instance.commands or
6
+ # instance.print_commands. An command can be searched for using
7
+ # instance.apropos
8
+ #
9
+ # Author:: atom smith (http://twitter.com/re5et)
10
+ # Copyright:: Copyright (c) 2010 atom smith
11
+ # License:: Distributes under the same terms as Ruby
12
+
13
+ require 'rubygems'
14
+ require 'net/http'
15
+ require 'json'
16
+
17
+ # The XBMC_JSONRPC module is a namespace / wrapper
18
+
19
+ module XBMC_JSONRPC
20
+
21
+ # Attempt to create connection with xbmc server, and retrieve available
22
+ # commands. Accepts connection information arguments and if successful
23
+ # returns a new connection
24
+ def self.new(options = {})
25
+ @connection = XBMC_JSONRPC::Connection.new(options)
26
+ if @connection.command('JSONRPC.Ping')
27
+ commands = @connection.command('JSONRPC.Introspect')['result']['commands']
28
+ @commands = {}
29
+
30
+ commands.each do |command|
31
+ command_name = command.shift[1]
32
+ @commands[command_name] = command
33
+ end
34
+ return self
35
+ end
36
+ return false
37
+ end
38
+
39
+ # Make an API call to the instance XBMC server
40
+ def self.command(method,args = {})
41
+ @connection.command(method, args)
42
+ end
43
+
44
+ # returns all available commands returned by JSON.Introspect
45
+ def self.commands
46
+ @commands
47
+ end
48
+
49
+ # nicely print out all available commands.
50
+ # useful at command line / irb / etc
51
+ def self.get_commands
52
+ @commands.each {|k,v| self.pp_command k }
53
+ return nil
54
+ end
55
+
56
+ # finds and prettily prints appropriate commands based on provided keyword
57
+ def self.apropos(find)
58
+ regexp = /#{find}/im
59
+ matches = []
60
+ @commands.each do |k,v|
61
+ matches.push(k) if k =~ regexp || v['description'] =~ regexp
62
+ end
63
+ if matches.empty?
64
+ puts "\n\nNo commands found, try being less specific\n\n"
65
+ else
66
+ matches.each {|command| self.pp_command command }
67
+ end
68
+ return nil
69
+ end
70
+
71
+ # prettily print out requested command
72
+ def self.pp_command(command)
73
+ description = @commands[command]['description']
74
+ description = "<no description exists for #{command}>" unless !description.empty?
75
+
76
+ puts "\n\t#{command}"
77
+ puts "\t\t#{description}\n\n"
78
+ end
79
+
80
+ # Class to create and store connection information for xbmc server
81
+ # also handles actual json back and forth.
82
+ class Connection
83
+
84
+ def initialize(options)
85
+
86
+ connection_info = {
87
+ :server => '127.0.0.1',
88
+ :port => '8080',
89
+ :user => 'xbmc',
90
+ :pass => ''
91
+ }
92
+
93
+ @connection_info = connection_info.merge(options)
94
+
95
+ @url = URI.parse("http://#{@connection_info[:server]}:#{@connection_info[:port]}/jsonrpc")
96
+ end
97
+
98
+ def command(method, params = {})
99
+ req = Net::HTTP::Post.new(@url.path)
100
+ req.basic_auth @connection_info[:user], @connection_info[:pass]
101
+ req.add_field 'Content-Type', 'application/json'
102
+ req.body = {
103
+ "id" => 1,
104
+ "jsonrpc" => "2.0",
105
+ "method" => method,
106
+ "params" => params
107
+ }.to_json
108
+
109
+ res = Net::HTTP.new(@url.host, @url.port).start {|http| http.request(req) }
110
+
111
+ if res.kind_of? Net::HTTPSuccess
112
+ return JSON.parse(res.body)
113
+ else
114
+ return res.error!
115
+ end
116
+ rescue StandardError
117
+ print "Unable to connect to server specified\n", $!
118
+ return false
119
+ end
120
+
121
+ end
122
+
123
+ # utility class for others to inherit from. For now uses method missing
124
+ # to make all calls to the send_command because there is no meaningful
125
+ # difference between namespaces / methods at the moment.
126
+ class APIBase
127
+
128
+ # get the correct api namespace to use
129
+ def self.namespace
130
+ @namespace = @namespace || self.name.to_s.split('::')[1]
131
+ end
132
+
133
+ # pass on namespace + method and arguments
134
+ def self.method_missing(method, args = {})
135
+ XBMC_JSONRPC.command("#{self.namespace}.#{method}", args)
136
+ end
137
+
138
+ # show commands for namespace
139
+ def self.commands
140
+ XBMC_JSONRPC.commands.keys.grep(/#{self.namespace}\./) {|command| XBMC_JSONRPC.pp_command(command) }
141
+ end
142
+
143
+ end
144
+
145
+ class JSONRPC < APIBase
146
+
147
+ # def self.Introspect
148
+ # end
149
+
150
+ # def self.Version
151
+ # end
152
+
153
+ # def self.Permission
154
+ # end
155
+
156
+ # def self.Ping
157
+ # end
158
+
159
+ # def self.Announce
160
+ # end
161
+
162
+ end
163
+
164
+ class Player < APIBase
165
+
166
+ # def self.GetActivePlayers
167
+ # end
168
+
169
+ end
170
+
171
+ class AudioPlayer < APIBase
172
+
173
+ # same methods as VideoPlayer
174
+
175
+ end
176
+
177
+ class VideoPlayer < APIBase
178
+
179
+ # def self.PlayPause
180
+ # end
181
+
182
+ # def self.Stop
183
+ # end
184
+
185
+ # def self.SkipPrevious
186
+ # end
187
+
188
+ # def self.SkipNext
189
+ # end
190
+
191
+ # def self.BigSkipBackward
192
+ # end
193
+
194
+ # def self.BigSkipForward
195
+ # end
196
+
197
+ # def self.SmallSkipBackward
198
+ # end
199
+
200
+ # def self.SmallSkipForward
201
+ # end
202
+
203
+ # def self.Rewind
204
+ # end
205
+
206
+ # def self.Forward
207
+ # end
208
+
209
+ # def self.GetTime
210
+ # end
211
+
212
+ # def self.GetTimeMS
213
+ # end
214
+
215
+ # def self.GetPercentage
216
+ # end
217
+
218
+ # def self.SeekTime
219
+ # end
220
+
221
+ # def self.SeekPercentage
222
+ # end
223
+
224
+ end
225
+
226
+ class PicturePlayer < APIBase
227
+
228
+ # def self.PlayPause
229
+ # end
230
+
231
+ # def self.Stop
232
+ # end
233
+
234
+ # def self.SkipPrevious
235
+ # end
236
+
237
+ # def self.SkipNext
238
+ # end
239
+
240
+ # def self.MoveLeft
241
+ # end
242
+
243
+ # def self.MoveRight
244
+ # end
245
+
246
+ # def self.MoveDown
247
+ # end
248
+
249
+ # def self.MoveUp
250
+ # end
251
+
252
+ # def self.ZoomOut
253
+ # end
254
+
255
+ # def self.ZoomIn
256
+ # end
257
+
258
+ # def self.Zoom
259
+ # end
260
+
261
+ # def self.Rotate
262
+ # end
263
+
264
+ end
265
+
266
+ class VideoPlaylist < APIBase
267
+
268
+ # def self.Play
269
+ # end
270
+
271
+ # def self.SkipPrevious
272
+ # end
273
+
274
+ # def self.SkipNext
275
+ # end
276
+
277
+ # def self.GetItems
278
+ # end
279
+
280
+ # def self.Add
281
+ # end
282
+
283
+ # def self.Clear
284
+ # end
285
+
286
+ # def self.Shuffle
287
+ # end
288
+
289
+ # def self.UnShuffle
290
+ # end
291
+
292
+ end
293
+
294
+ class AudioPlaylist < APIBase
295
+
296
+ # def self.Play
297
+ # end
298
+
299
+ # def self.SkipPrevious
300
+ # end
301
+
302
+ # def self.SkipNext
303
+ # end
304
+
305
+ # def self.GetItems
306
+ # end
307
+
308
+ # def self.Add
309
+ # end
310
+
311
+ # def self.Clear
312
+ # end
313
+
314
+ # def self.Shuffle
315
+ # end
316
+
317
+ # def self.UnShuffle
318
+ # end
319
+
320
+ end
321
+
322
+ class Playlist < APIBase
323
+
324
+ # def self.Create
325
+ # end
326
+
327
+ # def self.Destroy
328
+ # end
329
+
330
+ # def self.GetItems
331
+ # end
332
+
333
+ # def self.Add
334
+ # end
335
+
336
+ # def self.Remove
337
+ # end
338
+
339
+ # def self.Swap
340
+ # end
341
+
342
+ # def self.Shuffle
343
+ # end
344
+
345
+ end
346
+
347
+ class Files < APIBase
348
+
349
+ # def self.GetSources
350
+ # end
351
+
352
+ # def self.Download
353
+ # end
354
+
355
+ # def self.GetDirectory
356
+ # end
357
+
358
+ end
359
+
360
+ class AudioLibrary < APIBase
361
+
362
+ # def self.GetArtists
363
+ # end
364
+
365
+ # def self.GetAlbums
366
+ # end
367
+
368
+ # def self.GetSongs
369
+ # end
370
+
371
+ # def self.ScanForContent
372
+ # end
373
+
374
+ end
375
+
376
+ class VideoLibrary < APIBase
377
+
378
+ # def self.GetMovies
379
+ # end
380
+
381
+ # def self.GetTVShows
382
+ # end
383
+
384
+ # def self.GetSeasons
385
+ # end
386
+
387
+ # def self.GetEpisodes
388
+ # end
389
+
390
+ # def self.GetMusicVideoAlbums
391
+ # end
392
+
393
+ # def self.GetMusicVideos
394
+ # end
395
+
396
+ # def self.GetRecentlyAddedMovies
397
+ # end
398
+
399
+ # def self.GetRecentlyAddedEpisodes
400
+ # end
401
+
402
+ # def self.GetRecentlyAddedMusicVideos
403
+ # end
404
+
405
+ # def self.ScanForContent
406
+ # end
407
+
408
+ end
409
+
410
+ class System < APIBase
411
+
412
+ # def self.Shutdown
413
+ # end
414
+
415
+ # def self.Suspend
416
+ # end
417
+
418
+ # def self.Hibernate
419
+ # end
420
+
421
+ # def self.Reboot
422
+ # end
423
+
424
+ # def self.GetInfoLabels
425
+ # end
426
+
427
+ # def self.GetInfoBooleans
428
+ # end
429
+
430
+ end
431
+
432
+ class XBMC < APIBase
433
+
434
+ # def self.GetVolume
435
+ # end
436
+
437
+ # def self.SetVolume
438
+ # end
439
+
440
+ # def self.ToggleMute
441
+ # end
442
+
443
+ # def self.Play
444
+ # end
445
+
446
+ # def self.StartSlideShow
447
+ # end
448
+
449
+ # def self.Log
450
+ # end
451
+
452
+ # def self.Quit
453
+ # end
454
+
455
+ end
456
+
457
+ end
data/test/helper.rb ADDED
@@ -0,0 +1,10 @@
1
+ require 'rubygems'
2
+ require 'test/unit'
3
+ require 'shoulda'
4
+
5
+ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
6
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
7
+ require 'xbmc-jsonrpc'
8
+
9
+ class Test::Unit::TestCase
10
+ end
@@ -0,0 +1,7 @@
1
+ require 'helper'
2
+
3
+ class TestXbmcJsonrpc < Test::Unit::TestCase
4
+ should "probably rename this file and start testing for real" do
5
+ flunk "hey buddy, you should probably rename this file and start testing for real"
6
+ end
7
+ end
@@ -0,0 +1,54 @@
1
+ # Generated by jeweler
2
+ # DO NOT EDIT THIS FILE DIRECTLY
3
+ # Instead, edit Jeweler::Tasks in Rakefile, and run the gemspec command
4
+ # -*- encoding: utf-8 -*-
5
+
6
+ Gem::Specification.new do |s|
7
+ s.name = %q{xbmc-jsonrpc}
8
+ s.version = "0.2.0"
9
+
10
+ s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
+ s.authors = ["atom smith"]
12
+ s.date = %q{2010-10-14}
13
+ s.description = %q{A module for interacting with xbmc's json-rpc server}
14
+ s.email = %q{re5etsmyth@gmail.com}
15
+ s.extra_rdoc_files = [
16
+ "LICENSE",
17
+ "README.rdoc"
18
+ ]
19
+ s.files = [
20
+ ".document",
21
+ ".gitignore",
22
+ "LICENSE",
23
+ "README.rdoc",
24
+ "Rakefile",
25
+ "VERSION",
26
+ "lib/xbmc-jsonrpc.rb",
27
+ "test/helper.rb",
28
+ "test/test_xbmc-jsonrpc.rb",
29
+ "xbmc-jsonrpc.gemspec"
30
+ ]
31
+ s.homepage = %q{http://github.com/re5et/xbmc-jsonrpc}
32
+ s.rdoc_options = ["--charset=UTF-8"]
33
+ s.require_paths = ["lib"]
34
+ s.rubygems_version = %q{1.3.7}
35
+ s.summary = %q{A module for interacting with xbmc's json-rpc server}
36
+ s.test_files = [
37
+ "test/helper.rb",
38
+ "test/test_xbmc-jsonrpc.rb"
39
+ ]
40
+
41
+ if s.respond_to? :specification_version then
42
+ current_version = Gem::Specification::CURRENT_SPECIFICATION_VERSION
43
+ s.specification_version = 3
44
+
45
+ if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
46
+ s.add_development_dependency(%q<thoughtbot-shoulda>, [">= 0"])
47
+ else
48
+ s.add_dependency(%q<thoughtbot-shoulda>, [">= 0"])
49
+ end
50
+ else
51
+ s.add_dependency(%q<thoughtbot-shoulda>, [">= 0"])
52
+ end
53
+ end
54
+
metadata ADDED
@@ -0,0 +1,91 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: xbmc-jsonrpc
3
+ version: !ruby/object:Gem::Version
4
+ hash: 23
5
+ prerelease: false
6
+ segments:
7
+ - 0
8
+ - 2
9
+ - 0
10
+ version: 0.2.0
11
+ platform: ruby
12
+ authors:
13
+ - atom smith
14
+ autorequire:
15
+ bindir: bin
16
+ cert_chain: []
17
+
18
+ date: 2010-10-14 00:00:00 -04:00
19
+ default_executable:
20
+ dependencies:
21
+ - !ruby/object:Gem::Dependency
22
+ name: thoughtbot-shoulda
23
+ prerelease: false
24
+ requirement: &id001 !ruby/object:Gem::Requirement
25
+ none: false
26
+ requirements:
27
+ - - ">="
28
+ - !ruby/object:Gem::Version
29
+ hash: 3
30
+ segments:
31
+ - 0
32
+ version: "0"
33
+ type: :development
34
+ version_requirements: *id001
35
+ description: A module for interacting with xbmc's json-rpc server
36
+ email: re5etsmyth@gmail.com
37
+ executables: []
38
+
39
+ extensions: []
40
+
41
+ extra_rdoc_files:
42
+ - LICENSE
43
+ - README.rdoc
44
+ files:
45
+ - .document
46
+ - .gitignore
47
+ - LICENSE
48
+ - README.rdoc
49
+ - Rakefile
50
+ - VERSION
51
+ - lib/xbmc-jsonrpc.rb
52
+ - test/helper.rb
53
+ - test/test_xbmc-jsonrpc.rb
54
+ - xbmc-jsonrpc.gemspec
55
+ has_rdoc: true
56
+ homepage: http://github.com/re5et/xbmc-jsonrpc
57
+ licenses: []
58
+
59
+ post_install_message:
60
+ rdoc_options:
61
+ - --charset=UTF-8
62
+ require_paths:
63
+ - lib
64
+ required_ruby_version: !ruby/object:Gem::Requirement
65
+ none: false
66
+ requirements:
67
+ - - ">="
68
+ - !ruby/object:Gem::Version
69
+ hash: 3
70
+ segments:
71
+ - 0
72
+ version: "0"
73
+ required_rubygems_version: !ruby/object:Gem::Requirement
74
+ none: false
75
+ requirements:
76
+ - - ">="
77
+ - !ruby/object:Gem::Version
78
+ hash: 3
79
+ segments:
80
+ - 0
81
+ version: "0"
82
+ requirements: []
83
+
84
+ rubyforge_project:
85
+ rubygems_version: 1.3.7
86
+ signing_key:
87
+ specification_version: 3
88
+ summary: A module for interacting with xbmc's json-rpc server
89
+ test_files:
90
+ - test/helper.rb
91
+ - test/test_xbmc-jsonrpc.rb