bencode 0.6.0 → 0.7.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/.yardopts +5 -0
- data/Gemfile +6 -0
- data/README.md +4 -3
- data/VERSION +1 -1
- data/lib/bencode.rb +9 -3
- data/lib/bencode/{encode → core_ext}/array.rb +1 -1
- data/lib/bencode/{encode → core_ext}/hash.rb +2 -2
- data/lib/bencode/{encode → core_ext}/integer.rb +0 -0
- data/lib/bencode/{io.rb → core_ext/io.rb} +0 -0
- data/lib/bencode/{encode → core_ext}/object.rb +0 -0
- data/lib/bencode/{encode → core_ext}/string.rb +0 -0
- data/lib/bencode/decode.rb +68 -54
- data/test/bittorrent_test.rb +3 -4
- data/test/decoding_test.rb +3 -1
- data/test/encoding_test.rb +1 -1
- data/test/environment.rb +6 -2
- data/test/shoulda_macros/decoding.rb +3 -3
- data/test/shoulda_macros/encoding.rb +1 -1
- data/test/utf8_decoding_test.rb +3 -4
- metadata +29 -28
- data/.gitignore +0 -3
- data/lib/bencode/decode_error.rb +0 -4
- data/lib/bencode/encode_error.rb +0 -4
data/.yardopts
ADDED
data/Gemfile
ADDED
data/README.md
CHANGED
@@ -42,8 +42,9 @@ Released under the MIT license.
|
|
42
42
|
Contributors
|
43
43
|
------------
|
44
44
|
|
45
|
-
- Daniel Schierbeck
|
46
|
-
- Mike Hodgson
|
45
|
+
- Daniel Schierbeck ([dasch](https://github.com/dasch))
|
46
|
+
- Mike Hodgson ([mikehodgson](https://github.com/mikehodgson))
|
47
47
|
- Andrew Danforth
|
48
48
|
- Eric Himmelreich
|
49
|
-
- Allen Madsen
|
49
|
+
- Allen Madsen ([blatyo](https://github.com/blatyo))
|
50
|
+
- Ian Levesque ([ianlevesque](https://github.com/ianlevesque))
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.7.0
|
data/lib/bencode.rb
CHANGED
@@ -1,9 +1,15 @@
|
|
1
1
|
|
2
|
-
#
|
2
|
+
# Support for loading and dumping bencoded data.
|
3
|
+
#
|
4
|
+
# See {BEncode.load} and {BEncode.dump}.
|
3
5
|
module BEncode
|
4
|
-
|
6
|
+
class DecodeError < StandardError
|
7
|
+
end
|
8
|
+
|
9
|
+
class EncodeError < StandardError
|
10
|
+
end
|
5
11
|
end
|
6
12
|
|
7
13
|
glob = File.join(File.dirname(__FILE__), 'bencode/**/*.rb')
|
8
14
|
|
9
|
-
Dir[glob].sort.each{|file| require file }
|
15
|
+
Dir[glob].sort.each {|file| require file }
|
@@ -7,8 +7,8 @@ class Hash
|
|
7
7
|
# All keys must be strings. The keys of the bencoded hash will
|
8
8
|
# be in lexicographical order.
|
9
9
|
def bencode
|
10
|
-
pairs = sort.map{|key, val| [key.
|
11
|
-
"d#{pairs.join
|
10
|
+
pairs = sort.map{|key, val| [key.to_s.bencode, val.bencode] }
|
11
|
+
"d#{pairs.join}e"
|
12
12
|
rescue NoMethodError => error
|
13
13
|
raise BEncode::EncodeError, "dictionary keys must be strings"
|
14
14
|
end
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
data/lib/bencode/decode.rb
CHANGED
@@ -2,69 +2,83 @@
|
|
2
2
|
require 'strscan'
|
3
3
|
|
4
4
|
module BEncode
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
5
|
+
# Encodes the Ruby object +obj+ into a bencoded string.
|
6
|
+
#
|
7
|
+
# @param [Hash, Array, Integer, String] obj the object to encode
|
8
|
+
# @return [String] a bencoded string
|
9
|
+
# @raise [EncodeError] if +obj+ is not a supported object type
|
10
|
+
def self.dump(obj)
|
11
|
+
obj.bencode
|
12
|
+
end
|
13
|
+
|
14
|
+
# Decodes +str+ into a Ruby structure.
|
15
|
+
#
|
16
|
+
# @param [String] str a bencoded string
|
17
|
+
# @option opts [Boolean] :ignore_trailing_junk (false) whether
|
18
|
+
# to ignore invalid bencode at the end of +str+
|
19
|
+
# @return [Object] a Ruby object
|
20
|
+
# @raise [DecodeError] if +str+ is malformed
|
21
|
+
def self.load(str, opts = {})
|
22
|
+
scanner = StringScanner.new(str)
|
23
|
+
obj = parse(scanner)
|
24
|
+
raise BEncode::DecodeError unless (opts[:ignore_trailing_junk] || scanner.eos?)
|
25
|
+
return obj
|
26
|
+
end
|
10
27
|
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
28
|
+
# Decodes the file located at +path+.
|
29
|
+
#
|
30
|
+
# @param [String] path path to the bencoded file
|
31
|
+
# @option (see .load)
|
32
|
+
# @return (see .load)
|
33
|
+
def self.load_file(path, opts = {})
|
34
|
+
load(File.open(path, 'rb').read, opts)
|
35
|
+
end
|
18
36
|
|
19
|
-
|
20
|
-
def load_file(path)
|
21
|
-
load(File.open(path, 'rb') {|f| f.read})
|
22
|
-
end
|
37
|
+
private
|
23
38
|
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
39
|
+
def self.parse(scanner) # :nodoc:
|
40
|
+
val = case scanner.peek(1)[0]
|
41
|
+
when ?i
|
42
|
+
scanner.pos += 1
|
43
|
+
num = scanner.scan_until(/e/) or raise BEncode::DecodeError
|
44
|
+
num.chop.to_i
|
45
|
+
when ?l
|
46
|
+
scanner.pos += 1
|
47
|
+
ary = []
|
48
|
+
ary.push(parse(scanner)) until scanner.scan(/e/)
|
49
|
+
ary
|
50
|
+
when ?d
|
51
|
+
scanner.pos += 1
|
52
|
+
hsh = {}
|
53
|
+
until scanner.scan(/e/)
|
54
|
+
key = parse(scanner)
|
40
55
|
|
41
|
-
|
42
|
-
|
43
|
-
|
56
|
+
unless key.is_a? String or key.is_a? Fixnum
|
57
|
+
raise BEncode::DecodeError, "key must be a string or number"
|
58
|
+
end
|
44
59
|
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
60
|
+
hsh.store(key.to_s, parse(scanner))
|
61
|
+
end
|
62
|
+
hsh
|
63
|
+
when ?0 .. ?9
|
64
|
+
num = scanner.scan_until(/:/) or
|
65
|
+
raise BEncode::DecodeError, "invalid string length (no colon)"
|
51
66
|
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
67
|
+
begin
|
68
|
+
length = num.chop.to_i
|
69
|
+
str = scanner.peek(length)
|
70
|
+
scanner.pos += num.chop.to_i
|
71
|
+
rescue
|
72
|
+
raise BEncode::DecodeError, "invalid string length"
|
73
|
+
end
|
59
74
|
|
60
|
-
|
61
|
-
|
62
|
-
raise BEncode::DecodeError, "Invalid specifier #{scanner.peek(1).inspect} at position #{scanner.pos+1}"
|
63
|
-
end
|
64
|
-
end
|
75
|
+
str
|
76
|
+
end
|
65
77
|
|
66
|
-
|
78
|
+
raise BEncode::DecodeError if val.nil?
|
79
|
+
val
|
67
80
|
end
|
81
|
+
|
68
82
|
end
|
69
83
|
|
70
84
|
class String
|
data/test/bittorrent_test.rb
CHANGED
@@ -2,10 +2,9 @@
|
|
2
2
|
require 'test/environment'
|
3
3
|
|
4
4
|
|
5
|
-
class BitTorrentTest <
|
5
|
+
class BitTorrentTest < MiniTest::Unit::TestCase
|
6
6
|
should "load a bencoded torrent file" do
|
7
|
-
|
8
|
-
|
9
|
-
end
|
7
|
+
BEncode.load_file("test/fixtures/python.torrent")
|
8
|
+
pass
|
10
9
|
end
|
11
10
|
end
|
data/test/decoding_test.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
|
2
2
|
require 'test/environment'
|
3
3
|
|
4
|
-
class DecodingTest <
|
4
|
+
class DecodingTest < MiniTest::Unit::TestCase
|
5
5
|
context "The BEncode decoder" do
|
6
6
|
should_decode 42, "i42e"
|
7
7
|
should_decode 0, "i0e"
|
@@ -11,5 +11,7 @@ class DecodingTest < Test::Unit::TestCase
|
|
11
11
|
should_decode "", "0:"
|
12
12
|
|
13
13
|
should_decode [1, 2, 3], "li1ei2ei3ee"
|
14
|
+
|
15
|
+
should_decode 42, "i42eBOGUS", :ignore_trailing_junk => true
|
14
16
|
end
|
15
17
|
end
|
data/test/encoding_test.rb
CHANGED
data/test/environment.rb
CHANGED
@@ -1,7 +1,11 @@
|
|
1
1
|
|
2
2
|
require 'rubygems'
|
3
|
-
require '
|
4
|
-
|
3
|
+
require 'bundler/setup'
|
4
|
+
|
5
|
+
Bundler.require(:default, :test)
|
6
|
+
|
7
|
+
MiniTest::Unit.autorun
|
8
|
+
|
5
9
|
require File.dirname(__FILE__) + '/../lib/bencode'
|
6
10
|
Dir.glob(File.dirname(__FILE__) + '/shoulda_macros/*.rb').each do |macro|
|
7
11
|
require macro
|
@@ -1,8 +1,8 @@
|
|
1
1
|
|
2
|
-
class
|
3
|
-
def self.should_decode(expected, encoded)
|
2
|
+
class MiniTest::Unit::TestCase
|
3
|
+
def self.should_decode(expected, encoded, opts = {})
|
4
4
|
should "decode #{encoded.inspect} into #{expected.inspect}" do
|
5
|
-
assert_equal expected, BEncode.load(encoded)
|
5
|
+
assert_equal expected, BEncode.load(encoded, opts)
|
6
6
|
end
|
7
7
|
end
|
8
8
|
end
|
data/test/utf8_decoding_test.rb
CHANGED
@@ -1,12 +1,11 @@
|
|
1
1
|
|
2
2
|
require 'test/environment'
|
3
3
|
|
4
|
-
class UTF8DecodingTest <
|
4
|
+
class UTF8DecodingTest < MiniTest::Unit::TestCase
|
5
5
|
context "The BEncode decoder" do
|
6
6
|
should "be able to handle UTF8-encoded data" do
|
7
|
-
|
8
|
-
|
9
|
-
end
|
7
|
+
BEncode.load_file('test/fixtures/test.torrent')
|
8
|
+
pass
|
10
9
|
end
|
11
10
|
end
|
12
11
|
end
|
metadata
CHANGED
@@ -1,7 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: bencode
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
|
4
|
+
hash: 3
|
5
|
+
prerelease:
|
6
|
+
segments:
|
7
|
+
- 0
|
8
|
+
- 7
|
9
|
+
- 0
|
10
|
+
version: 0.7.0
|
5
11
|
platform: ruby
|
6
12
|
authors:
|
7
13
|
- Daniel Schierbeck
|
@@ -9,8 +15,7 @@ autorequire:
|
|
9
15
|
bindir: bin
|
10
16
|
cert_chain: []
|
11
17
|
|
12
|
-
date:
|
13
|
-
default_executable:
|
18
|
+
date: 2011-06-15 00:00:00 Z
|
14
19
|
dependencies: []
|
15
20
|
|
16
21
|
description: A simple encoder and decoder for the BitTorrent serialization format.
|
@@ -23,21 +28,20 @@ extra_rdoc_files:
|
|
23
28
|
- LICENSE
|
24
29
|
- README.md
|
25
30
|
files:
|
26
|
-
- .
|
31
|
+
- .yardopts
|
32
|
+
- Gemfile
|
27
33
|
- LICENSE
|
28
34
|
- README.md
|
29
35
|
- Rakefile
|
30
36
|
- VERSION
|
31
37
|
- lib/bencode.rb
|
38
|
+
- lib/bencode/core_ext/array.rb
|
39
|
+
- lib/bencode/core_ext/hash.rb
|
40
|
+
- lib/bencode/core_ext/integer.rb
|
41
|
+
- lib/bencode/core_ext/io.rb
|
42
|
+
- lib/bencode/core_ext/object.rb
|
43
|
+
- lib/bencode/core_ext/string.rb
|
32
44
|
- lib/bencode/decode.rb
|
33
|
-
- lib/bencode/decode_error.rb
|
34
|
-
- lib/bencode/encode/array.rb
|
35
|
-
- lib/bencode/encode/hash.rb
|
36
|
-
- lib/bencode/encode/integer.rb
|
37
|
-
- lib/bencode/encode/object.rb
|
38
|
-
- lib/bencode/encode/string.rb
|
39
|
-
- lib/bencode/encode_error.rb
|
40
|
-
- lib/bencode/io.rb
|
41
45
|
- test/benchmark/decoding.rb
|
42
46
|
- test/benchmark/encoding.rb
|
43
47
|
- test/bittorrent_test.rb
|
@@ -49,41 +53,38 @@ files:
|
|
49
53
|
- test/shoulda_macros/decoding.rb
|
50
54
|
- test/shoulda_macros/encoding.rb
|
51
55
|
- test/utf8_decoding_test.rb
|
52
|
-
has_rdoc: true
|
53
56
|
homepage: http://github.com/dasch/ruby-bencode
|
54
57
|
licenses: []
|
55
58
|
|
56
59
|
post_install_message:
|
57
|
-
rdoc_options:
|
58
|
-
|
60
|
+
rdoc_options: []
|
61
|
+
|
59
62
|
require_paths:
|
60
63
|
- lib
|
61
64
|
required_ruby_version: !ruby/object:Gem::Requirement
|
65
|
+
none: false
|
62
66
|
requirements:
|
63
67
|
- - ">="
|
64
68
|
- !ruby/object:Gem::Version
|
69
|
+
hash: 3
|
70
|
+
segments:
|
71
|
+
- 0
|
65
72
|
version: "0"
|
66
|
-
version:
|
67
73
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
74
|
+
none: false
|
68
75
|
requirements:
|
69
76
|
- - ">="
|
70
77
|
- !ruby/object:Gem::Version
|
78
|
+
hash: 3
|
79
|
+
segments:
|
80
|
+
- 0
|
71
81
|
version: "0"
|
72
|
-
version:
|
73
82
|
requirements: []
|
74
83
|
|
75
84
|
rubyforge_project:
|
76
|
-
rubygems_version: 1.
|
85
|
+
rubygems_version: 1.8.5
|
77
86
|
signing_key:
|
78
87
|
specification_version: 3
|
79
88
|
summary: Encode and decode bencoded data
|
80
|
-
test_files:
|
81
|
-
|
82
|
-
- test/decoding_test.rb
|
83
|
-
- test/utf8_decoding_test.rb
|
84
|
-
- test/shoulda_macros/decoding.rb
|
85
|
-
- test/shoulda_macros/encoding.rb
|
86
|
-
- test/environment.rb
|
87
|
-
- test/encoding_test.rb
|
88
|
-
- test/benchmark/decoding.rb
|
89
|
-
- test/benchmark/encoding.rb
|
89
|
+
test_files: []
|
90
|
+
|
data/.gitignore
DELETED
data/lib/bencode/decode_error.rb
DELETED
data/lib/bencode/encode_error.rb
DELETED