leaderboard 3.0.2 → 3.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +15 -0
- data/.ruby-gemset +1 -0
- data/.ruby-version +1 -0
- data/.travis.yml +7 -0
- data/README.markdown +29 -20
- data/lib/leaderboard/version.rb +1 -1
- data/lib/leaderboard.rb +7 -3
- data/spec/leaderboard_spec.rb +31 -3
- data/spec/version_spec.rb +1 -1
- metadata +8 -20
- data/.rvmrc +0 -2
checksums.yaml
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
---
|
2
|
+
!binary "U0hBMQ==":
|
3
|
+
metadata.gz: !binary |-
|
4
|
+
NjI2NWFlODMyNTM3NWMzZmM4YzUwMzljMWJkMDQ2MmVhMjVlNjQ1ZQ==
|
5
|
+
data.tar.gz: !binary |-
|
6
|
+
ZDNhMmYzZjU5MGJjYjU3YTIzMWI0NWJhZDNhNDAwNmRjYzFmMjAyOA==
|
7
|
+
!binary "U0hBNTEy":
|
8
|
+
metadata.gz: !binary |-
|
9
|
+
YTk2YTBhNzZhZGUyODgwYzAwYTgzNDAyOTYwYTQzYjVhODdmZGJiZmEwMzc1
|
10
|
+
YzdiODM3MTA2NGI1M2I2NjhjZmVmN2RlMDVlMzBjYmUxMGU1YjkyYjU4ODQy
|
11
|
+
NTRmMWM5NzM3NTE1MDYzYjc1ZjkyNDU1MjA3MDE1NTc0Nzk1ZWU=
|
12
|
+
data.tar.gz: !binary |-
|
13
|
+
MmIwMTc1ZGVjZmE0N2U4NjRjNGM2OGY3M2ZlZTQ4YTM5ZTQ0ZWI3MDRkNzA4
|
14
|
+
MjhjNDhkMWFiMDhiYTExOTdhMDFjNGU2YWEyNTI2MDVhNzA5YmEwYjA1Nzg3
|
15
|
+
NDljMDM5ZWNmZjY3ZDI5NzVlY2VmZGIxZDczMmJlMTAxZjgxOGI=
|
data/.ruby-gemset
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
leaderboard_gem
|
data/.ruby-version
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
ruby-1.9.3
|
data/.travis.yml
ADDED
data/README.markdown
CHANGED
@@ -4,6 +4,8 @@ Leaderboards backed by [Redis](http://redis.io) in Ruby.
|
|
4
4
|
|
5
5
|
Builds off ideas proposed in http://blog.agoragames.com/2011/01/01/creating-high-score-tables-leaderboards-using-redis/.
|
6
6
|
|
7
|
+
[![Build Status](https://secure.travis-ci.org/agoragames/leaderboard.png)](http://travis-ci.org/agoragames/leaderboard)
|
8
|
+
|
7
9
|
## Installation
|
8
10
|
|
9
11
|
`gem install leaderboard`
|
@@ -119,10 +121,10 @@ Get some information about your leaderboard:
|
|
119
121
|
=> 1
|
120
122
|
```
|
121
123
|
|
122
|
-
The `rank_member` call will also accept an optional parameter, `member_data` that could
|
123
|
-
be used to store other information about a given member in the leaderboard. This
|
124
|
-
may be useful in situations where you are storing member IDs in the leaderboard and
|
125
|
-
you want to be able to store a member name for display. You could use JSON to
|
124
|
+
The `rank_member` call will also accept an optional parameter, `member_data` that could
|
125
|
+
be used to store other information about a given member in the leaderboard. This
|
126
|
+
may be useful in situations where you are storing member IDs in the leaderboard and
|
127
|
+
you want to be able to store a member name for display. You could use JSON to
|
126
128
|
encode a Hash of member data. Example:
|
127
129
|
|
128
130
|
```ruby
|
@@ -138,7 +140,7 @@ JSON.parse(highscore_lb.member_data_for('84849292'))
|
|
138
140
|
=> {"username"=>"member_name"}
|
139
141
|
|
140
142
|
highscore_lb.update_member_data('84849292', JSON.generate({'last_updated' => Time.now, 'username' => 'updated_member_name'}))
|
141
|
-
=> "OK"
|
143
|
+
=> "OK"
|
142
144
|
JSON.parse(highscore_lb.member_data_for('84849292'))
|
143
145
|
=> {"username"=>"updated_member_name", "last_updated"=>"2012-06-09 09:11:06 -0400"}
|
144
146
|
|
@@ -149,10 +151,10 @@ If you delete the leaderboard, ALL of the member data is deleted as well.
|
|
149
151
|
|
150
152
|
#### Optional member data notes
|
151
153
|
|
152
|
-
If you use optional member data, the use of the `remove_members_in_score_range` will leave data around in the member data
|
153
|
-
hash. This is because the internal Redis method, `zremrangebyscore`, only returns the number of items removed. It does
|
154
|
+
If you use optional member data, the use of the `remove_members_in_score_range` will leave data around in the member data
|
155
|
+
hash. This is because the internal Redis method, `zremrangebyscore`, only returns the number of items removed. It does
|
154
156
|
not return the members that it removed.
|
155
|
-
|
157
|
+
|
156
158
|
Get some information about a specific member(s) in the leaderboard:
|
157
159
|
|
158
160
|
```ruby
|
@@ -172,15 +174,17 @@ Get page 1 in the leaderboard:
|
|
172
174
|
highscore_lb.leaders(1)
|
173
175
|
=> [{:member=>"member_10", :rank=>1, :score=>10.0}, {:member=>"member_9", :rank=>2, :score=>9.0}, {:member=>"member_8", :rank=>3, :score=>8.0}, {:member=>"member_7", :rank=>4, :score=>7.0}, {:member=>"member_6", :rank=>5, :score=>6.0}, {:member=>"member_5", :rank=>6, :score=>5.0}, {:member=>"member_4", :rank=>7, :score=>4.0}, {:member=>"member_3", :rank=>8, :score=>3.0}, {:member=>"member_2", :rank=>9, :score=>2.0}, {:member=>"member_1", :rank=>10, :score=>1.0}]
|
174
176
|
```
|
175
|
-
|
176
|
-
You can pass various options to the calls `leaders`, `around_me` and `ranked_in_list`.
|
177
|
-
|
178
|
-
`:
|
177
|
+
|
178
|
+
You can pass various options to the calls `leaders`, `all_leaders`, `around_me`, `members_from_score_range`, `members_from_rank_range` and `ranked_in_list`. Valid options are:
|
179
|
+
|
180
|
+
* `:with_member_data` - `true` or `false` (default) to return the optional member data.
|
181
|
+
* `:page_size` - An integer value to change the page size for that call.
|
182
|
+
* `:members_only` - `true` or `false` (default) to return only the members without their score and rank.
|
183
|
+
* `:sort_option` - Valid values for `:sort_option` are `:none` (default), `:score` and `:rank`.
|
179
184
|
|
180
185
|
You can also use the `members` and `members_in` methods as aliases for the `leaders` and `leaders_in` methods.
|
181
186
|
|
182
|
-
There are also a few convenience methods to be able to retrieve all leaders from a given leaderboard. They are `all_leaders` and `all_leaders_from`. You
|
183
|
-
may also use the aliases `all_members` or `all_members_from`. Use any of these methods sparingly as all the information in the leaderboard will be returned.
|
187
|
+
There are also a few convenience methods to be able to retrieve all leaders from a given leaderboard. They are `all_leaders` and `all_leaders_from`. You may also use the aliases `all_members` or `all_members_from`. Use any of these methods sparingly as all the information in the leaderboard will be returned.
|
184
188
|
|
185
189
|
Add more members to your leaderboard:
|
186
190
|
|
@@ -225,21 +229,21 @@ Retrieve a range of members from the leaderboard within a given rank range:
|
|
225
229
|
|
226
230
|
```ruby
|
227
231
|
members = highscore_lb.members_from_rank_range(1, 5)
|
228
|
-
=> [{:member=>"member_95", :rank=>1, :score=>95.0}, {:member=>"member_94", :rank=>2, :score=>94.0}, {:member=>"member_93", :rank=>3, :score=>93.0}, {:member=>"member_92", :rank=>4, :score=>92.0}, {:member=>"member_91", :rank=>5, :score=>91.0}]
|
232
|
+
=> [{:member=>"member_95", :rank=>1, :score=>95.0}, {:member=>"member_94", :rank=>2, :score=>94.0}, {:member=>"member_93", :rank=>3, :score=>93.0}, {:member=>"member_92", :rank=>4, :score=>92.0}, {:member=>"member_91", :rank=>5, :score=>91.0}]
|
229
233
|
```
|
230
234
|
|
231
|
-
The option `:sort_option` is useful for retrieving an arbitrary list of
|
232
|
-
members from a given leaderboard where you would like the data sorted
|
235
|
+
The option `:sort_option` is useful for retrieving an arbitrary list of
|
236
|
+
members from a given leaderboard where you would like the data sorted
|
233
237
|
when returned. The follow examples demonstrate its use:
|
234
238
|
|
235
239
|
```ruby
|
236
240
|
friends = highscore_lb.ranked_in_list(['member_6', 'member_1', 'member_10'], :sort_by => :rank)
|
237
|
-
=> [{:member=>"member_10", :rank=>47, :score=>10.0}, {:member=>"member_6", :rank=>51, :score=>6.0}, {:member=>"member_1", :rank=>56, :score=>1.0}]
|
241
|
+
=> [{:member=>"member_10", :rank=>47, :score=>10.0}, {:member=>"member_6", :rank=>51, :score=>6.0}, {:member=>"member_1", :rank=>56, :score=>1.0}]
|
238
242
|
```
|
239
243
|
|
240
244
|
```ruby
|
241
245
|
friends = highscore_lb.ranked_in_list(['member_6', 'member_1', 'member_10'], :sort_by => :score)
|
242
|
-
=> [{:member=>"member_1", :rank=>56, :score=>1.0}, {:member=>"member_6", :rank=>51, :score=>6.0}, {:member=>"member_10", :rank=>47, :score=>10.0}]
|
246
|
+
=> [{:member=>"member_1", :rank=>56, :score=>1.0}, {:member=>"member_6", :rank=>51, :score=>6.0}, {:member=>"member_10", :rank=>47, :score=>10.0}]
|
243
247
|
```
|
244
248
|
|
245
249
|
### Conditionally rank a member in the leaderboard
|
@@ -410,10 +414,15 @@ end
|
|
410
414
|
|
411
415
|
The following ports have been made of the leaderboard gem.
|
412
416
|
|
417
|
+
Officially supported:
|
418
|
+
|
413
419
|
* CoffeeScript: https://github.com/agoragames/leaderboard-coffeescript
|
420
|
+
* Python: https://github.com/agoragames/leaderboard-python
|
421
|
+
|
422
|
+
Unofficially supported (they need some feature parity love):
|
423
|
+
|
414
424
|
* Java: https://github.com/agoragames/java-leaderboard
|
415
425
|
* PHP: https://github.com/agoragames/php-leaderboard
|
416
|
-
* Python: https://github.com/agoragames/leaderboard-python
|
417
426
|
* Scala: https://github.com/agoragames/scala-leaderboard
|
418
427
|
|
419
428
|
## Contributing to leaderboard
|
data/lib/leaderboard/version.rb
CHANGED
data/lib/leaderboard.rb
CHANGED
@@ -29,10 +29,12 @@ class Leaderboard
|
|
29
29
|
# Default options when requesting data from a leaderboard.
|
30
30
|
# +:with_member_data+ false: Return member data along with the member names.
|
31
31
|
# +:page_size+ nil: The default page size will be used.
|
32
|
+
# +:members_only+ false: Only return the member name, not their score and rank.
|
32
33
|
# +:sort_by+ :none: The default sort for a call to `ranked_in_list`.
|
33
34
|
DEFAULT_LEADERBOARD_REQUEST_OPTIONS = {
|
34
35
|
:with_member_data => false,
|
35
36
|
:page_size => nil,
|
37
|
+
:members_only => false,
|
36
38
|
:sort_by => :none
|
37
39
|
}
|
38
40
|
|
@@ -831,13 +833,15 @@ class Leaderboard
|
|
831
833
|
end
|
832
834
|
transaction.zscore(leaderboard_name, member)
|
833
835
|
end
|
834
|
-
end
|
836
|
+
end unless leaderboard_options[:members_only]
|
835
837
|
|
836
838
|
members.each_with_index do |member, index|
|
837
839
|
data = {}
|
838
840
|
data[:member] = member
|
839
|
-
|
840
|
-
|
841
|
+
unless leaderboard_options[:members_only]
|
842
|
+
data[:rank] = responses[index * 2] + 1 rescue nil
|
843
|
+
data[:score] = responses[index * 2 + 1].to_f if responses[index * 2 + 1]
|
844
|
+
end
|
841
845
|
|
842
846
|
if leaderboard_options[:with_member_data]
|
843
847
|
data[:member_data] = member_data_for_in(leaderboard_name, member)
|
data/spec/leaderboard_spec.rb
CHANGED
@@ -187,7 +187,7 @@ describe 'Leaderboard' do
|
|
187
187
|
|
188
188
|
member_25 = {:member => 'member_25', :score => 25.0, :rank => 1, :member_data => { :member_name => "Leaderboard member 25" }.to_s }
|
189
189
|
leaders[0].should == member_25
|
190
|
-
|
190
|
+
|
191
191
|
member_1 = {:member => 'member_1', :score => 1.0, :rank => 25, :member_data => { :member_name => "Leaderboard member 1" }.to_s }
|
192
192
|
leaders[24].should == member_1
|
193
193
|
end
|
@@ -590,7 +590,7 @@ describe 'Leaderboard' do
|
|
590
590
|
members = @leaderboard.members_from_rank_range(5, 9)
|
591
591
|
members.size.should be(5)
|
592
592
|
members[0][:member].should eql('member_21')
|
593
|
-
members[0][:score].to_i.should be(21)
|
593
|
+
members[0][:score].to_i.should be(21)
|
594
594
|
members[4][:member].should eql('member_17')
|
595
595
|
|
596
596
|
members = @leaderboard.members_from_rank_range(1, 1)
|
@@ -670,7 +670,7 @@ describe 'Leaderboard' do
|
|
670
670
|
|
671
671
|
it 'should not delete all the member data when calling remove_member' do
|
672
672
|
rank_members_in_leaderboard
|
673
|
-
|
673
|
+
|
674
674
|
@redis_connection.exists("name:member_data").should be_true
|
675
675
|
@redis_connection.hgetall("name:member_data").size.should be(5)
|
676
676
|
@leaderboard.total_members.should be(5)
|
@@ -679,4 +679,32 @@ describe 'Leaderboard' do
|
|
679
679
|
@redis_connection.hgetall("name:member_data").size.should be(4)
|
680
680
|
@leaderboard.total_members.should be(4)
|
681
681
|
end
|
682
|
+
|
683
|
+
it 'should return the members only if the :members_only option is passed' do
|
684
|
+
rank_members_in_leaderboard(25)
|
685
|
+
|
686
|
+
leaders = @leaderboard.leaders(1, :page_size => 10, :members_only => true)
|
687
|
+
leaders.size.should == 10
|
688
|
+
leaders.collect { |leader| leader.keys.should == [:member] }
|
689
|
+
|
690
|
+
leaders = @leaderboard.all_leaders(:members_only => true)
|
691
|
+
leaders.size.should == 25
|
692
|
+
leaders.collect { |leader| leader.keys.should == [:member] }
|
693
|
+
|
694
|
+
leaders = @leaderboard.members_from_score_range(10, 14, :members_only => true)
|
695
|
+
leaders.size.should == 5
|
696
|
+
leaders.collect { |leader| leader.keys.should == [:member] }
|
697
|
+
|
698
|
+
leaders = @leaderboard.members_from_rank_range(1, 5, :page_size => 10, :members_only => true)
|
699
|
+
leaders.size.should == 5
|
700
|
+
leaders.collect { |leader| leader.keys.should == [:member] }
|
701
|
+
|
702
|
+
leaders = @leaderboard.around_me('member_10', :page_size => 3, :members_only => true)
|
703
|
+
leaders.size.should == 3
|
704
|
+
leaders.collect { |leader| leader.keys.should == [:member] }
|
705
|
+
|
706
|
+
leaders = @leaderboard.ranked_in_list(['member_1', 'member_25'], :members_only => true)
|
707
|
+
leaders.size.should == 2
|
708
|
+
leaders.collect { |leader| leader.keys.should == [:member] }
|
709
|
+
end
|
682
710
|
end
|
data/spec/version_spec.rb
CHANGED
metadata
CHANGED
@@ -1,20 +1,18 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: leaderboard
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.0
|
5
|
-
prerelease:
|
4
|
+
version: 3.1.0
|
6
5
|
platform: ruby
|
7
6
|
authors:
|
8
7
|
- David Czarnecki
|
9
8
|
autorequire:
|
10
9
|
bindir: bin
|
11
10
|
cert_chain: []
|
12
|
-
date: 2013-
|
11
|
+
date: 2013-05-15 00:00:00.000000000 Z
|
13
12
|
dependencies:
|
14
13
|
- !ruby/object:Gem::Dependency
|
15
14
|
name: redis
|
16
15
|
requirement: !ruby/object:Gem::Requirement
|
17
|
-
none: false
|
18
16
|
requirements:
|
19
17
|
- - ! '>='
|
20
18
|
- !ruby/object:Gem::Version
|
@@ -22,7 +20,6 @@ dependencies:
|
|
22
20
|
type: :runtime
|
23
21
|
prerelease: false
|
24
22
|
version_requirements: !ruby/object:Gem::Requirement
|
25
|
-
none: false
|
26
23
|
requirements:
|
27
24
|
- - ! '>='
|
28
25
|
- !ruby/object:Gem::Version
|
@@ -30,7 +27,6 @@ dependencies:
|
|
30
27
|
- !ruby/object:Gem::Dependency
|
31
28
|
name: rake
|
32
29
|
requirement: !ruby/object:Gem::Requirement
|
33
|
-
none: false
|
34
30
|
requirements:
|
35
31
|
- - ! '>='
|
36
32
|
- !ruby/object:Gem::Version
|
@@ -38,7 +34,6 @@ dependencies:
|
|
38
34
|
type: :development
|
39
35
|
prerelease: false
|
40
36
|
version_requirements: !ruby/object:Gem::Requirement
|
41
|
-
none: false
|
42
37
|
requirements:
|
43
38
|
- - ! '>='
|
44
39
|
- !ruby/object:Gem::Version
|
@@ -46,7 +41,6 @@ dependencies:
|
|
46
41
|
- !ruby/object:Gem::Dependency
|
47
42
|
name: rspec
|
48
43
|
requirement: !ruby/object:Gem::Requirement
|
49
|
-
none: false
|
50
44
|
requirements:
|
51
45
|
- - ! '>='
|
52
46
|
- !ruby/object:Gem::Version
|
@@ -54,7 +48,6 @@ dependencies:
|
|
54
48
|
type: :development
|
55
49
|
prerelease: false
|
56
50
|
version_requirements: !ruby/object:Gem::Requirement
|
57
|
-
none: false
|
58
51
|
requirements:
|
59
52
|
- - ! '>='
|
60
53
|
- !ruby/object:Gem::Version
|
@@ -68,7 +61,9 @@ extra_rdoc_files: []
|
|
68
61
|
files:
|
69
62
|
- .gitignore
|
70
63
|
- .rspec
|
71
|
-
- .
|
64
|
+
- .ruby-gemset
|
65
|
+
- .ruby-version
|
66
|
+
- .travis.yml
|
72
67
|
- CHANGELOG.markdown
|
73
68
|
- Gemfile
|
74
69
|
- LICENSE.txt
|
@@ -83,33 +78,26 @@ files:
|
|
83
78
|
- spec/version_spec.rb
|
84
79
|
homepage: https://github.com/agoragames/leaderboard
|
85
80
|
licenses: []
|
81
|
+
metadata: {}
|
86
82
|
post_install_message:
|
87
83
|
rdoc_options: []
|
88
84
|
require_paths:
|
89
85
|
- lib
|
90
86
|
required_ruby_version: !ruby/object:Gem::Requirement
|
91
|
-
none: false
|
92
87
|
requirements:
|
93
88
|
- - ! '>='
|
94
89
|
- !ruby/object:Gem::Version
|
95
90
|
version: '0'
|
96
|
-
segments:
|
97
|
-
- 0
|
98
|
-
hash: 1304683116950225093
|
99
91
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
100
|
-
none: false
|
101
92
|
requirements:
|
102
93
|
- - ! '>='
|
103
94
|
- !ruby/object:Gem::Version
|
104
95
|
version: '0'
|
105
|
-
segments:
|
106
|
-
- 0
|
107
|
-
hash: 1304683116950225093
|
108
96
|
requirements: []
|
109
97
|
rubyforge_project: leaderboard
|
110
|
-
rubygems_version:
|
98
|
+
rubygems_version: 2.0.3
|
111
99
|
signing_key:
|
112
|
-
specification_version:
|
100
|
+
specification_version: 4
|
113
101
|
summary: Leaderboards backed by Redis in Ruby
|
114
102
|
test_files:
|
115
103
|
- spec/leaderboard_spec.rb
|
data/.rvmrc
DELETED