steam-condenser 1.1.0 → 1.2.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (62) hide show
  1. data/Gemfile.lock +30 -0
  2. data/LICENSE +1 -1
  3. data/README.md +4 -3
  4. data/lib/steam-condenser/version.rb +2 -2
  5. data/lib/steam/community/alien_swarm/alien_swarm_mission.rb +24 -22
  6. data/lib/steam/community/alien_swarm/alien_swarm_stats.rb +66 -65
  7. data/lib/steam/community/alien_swarm/alien_swarm_weapon.rb +6 -6
  8. data/lib/steam/community/app_news.rb +2 -2
  9. data/lib/steam/community/css/css_map.rb +4 -4
  10. data/lib/steam/community/css/css_stats.rb +43 -43
  11. data/lib/steam/community/css/css_weapon.rb +5 -5
  12. data/lib/steam/community/defense_grid/defense_grid_stats.rb +36 -35
  13. data/lib/steam/community/dods/dods_class.rb +14 -14
  14. data/lib/steam/community/dods/dods_stats.rb +5 -4
  15. data/lib/steam/community/dods/dods_weapon.rb +6 -6
  16. data/lib/steam/community/game_achievement.rb +38 -31
  17. data/lib/steam/community/game_inventory.rb +6 -6
  18. data/lib/steam/community/game_leaderboard.rb +34 -32
  19. data/lib/steam/community/game_leaderboard_entry.rb +6 -6
  20. data/lib/steam/community/game_stats.rb +39 -65
  21. data/lib/steam/community/game_weapon.rb +2 -2
  22. data/lib/steam/community/l4d/abstract_l4d_stats.rb +54 -49
  23. data/lib/steam/community/l4d/abstract_l4d_weapon.rb +7 -6
  24. data/lib/steam/community/l4d/l4d2_map.rb +10 -10
  25. data/lib/steam/community/l4d/l4d2_stats.rb +33 -33
  26. data/lib/steam/community/l4d/l4d2_weapon.rb +8 -7
  27. data/lib/steam/community/l4d/l4d_explosive.rb +5 -4
  28. data/lib/steam/community/l4d/l4d_map.rb +8 -7
  29. data/lib/steam/community/l4d/l4d_stats.rb +7 -7
  30. data/lib/steam/community/l4d/l4d_weapon.rb +5 -4
  31. data/lib/steam/community/portal2/portal2_stats.rb +3 -3
  32. data/lib/steam/community/steam_game.rb +106 -16
  33. data/lib/steam/community/steam_group.rb +51 -40
  34. data/lib/steam/community/steam_id.rb +119 -87
  35. data/lib/steam/community/tf2/tf2_class.rb +14 -14
  36. data/lib/steam/community/tf2/tf2_class_factory.rb +2 -2
  37. data/lib/steam/community/tf2/tf2_engineer.rb +5 -7
  38. data/lib/steam/community/tf2/tf2_golden_wrench.rb +1 -1
  39. data/lib/steam/community/tf2/tf2_medic.rb +4 -6
  40. data/lib/steam/community/tf2/tf2_sniper.rb +3 -5
  41. data/lib/steam/community/tf2/tf2_spy.rb +10 -6
  42. data/lib/steam/community/tf2/tf2_stats.rb +15 -7
  43. data/lib/steam/community/web_api.rb +15 -1
  44. data/lib/steam/community/xml_data.rb +17 -0
  45. data/lib/steam/servers/game_server.rb +4 -4
  46. data/lib/steam/servers/master_server.rb +2 -2
  47. data/lib/steam/servers/source_server.rb +0 -2
  48. data/lib/steam/sockets/goldsrc_socket.rb +2 -2
  49. data/lib/steam/steam_player.rb +2 -2
  50. data/steam-condenser.gemspec +3 -2
  51. data/test/helper.rb +10 -2
  52. data/test/steam/communtiy/test_steam_group.rb +4 -4
  53. data/test/steam/communtiy/test_steam_id.rb +28 -2
  54. data/test/steam/communtiy/test_web_api.rb +2 -2
  55. data/test/steam/packets/test_steam_packet.rb +37 -0
  56. data/test/steam/servers/test_game_server.rb +296 -308
  57. data/test/steam/servers/test_goldsrc_server.rb +59 -59
  58. data/test/steam/servers/test_master_server.rb +131 -131
  59. data/test/steam/servers/test_server.rb +72 -72
  60. data/test/steam/servers/test_source_server.rb +126 -140
  61. data/test/steam/sockets/test_master_server_socket.rb +1 -0
  62. metadata +39 -19
@@ -1,7 +1,7 @@
1
1
  # This code is free software; you can redistribute it and/or modify it under
2
2
  # the terms of the new BSD License.
3
3
  #
4
- # Copyright (c) 2011, Sebastian Staudt
4
+ # Copyright (c) 2011-2012, Sebastian Staudt
5
5
 
6
6
  # The GameLeaderboard class represents a single entry in a leaderboard
7
7
  #
@@ -30,13 +30,13 @@ class GameLeaderboardEntry
30
30
 
31
31
  # Creates new entry instance for the given XML data and leaderboard
32
32
  #
33
- # @param [REXML::Element] entry_data The XML data of the leaderboard of the
34
- # leaderboard entry
33
+ # @param [Hash<String, Object>] entry_data The XML data of the leaderboard of
34
+ # the leaderboard entry
35
35
  # @param [GameLeaderboard] leaderboard The leaderboard this entry belongs to
36
36
  def initialize(entry_data, leaderboard)
37
- @steam_id = SteamId.new entry_data.elements['steamid'].text.to_i, false
38
- @score = entry_data.elements['score'].text.to_i
39
- @rank = entry_data.elements['rank'].text.to_i
37
+ @steam_id = SteamId.new entry_data['steamid'].to_i, false
38
+ @score = entry_data['score'].to_i
39
+ @rank = entry_data['rank'].to_i
40
40
  @leaderboard = leaderboard
41
41
  end
42
42
 
@@ -1,13 +1,11 @@
1
1
  # This code is free software; you can redistribute it and/or modify it under
2
2
  # the terms of the new BSD License.
3
3
  #
4
- # Copyright (c) 2008-2011, Sebastian Staudt
5
-
6
- require 'open-uri'
7
- require 'rexml/document'
4
+ # Copyright (c) 2008-2012, Sebastian Staudt
8
5
 
9
6
  require 'steam/community/game_achievement'
10
7
  require 'steam/community/game_leaderboard'
8
+ require 'steam/community/xml_data'
11
9
 
12
10
  # This class represents the game statistics for a single user and a specific
13
11
  # game
@@ -18,25 +16,12 @@ require 'steam/community/game_leaderboard'
18
16
  # @author Sebastian Staudt
19
17
  class GameStats
20
18
 
21
- # Returns the Steam application ID of the game these stats belong to
22
- #
23
- # @return [Fixnum] The Steam application ID of the game
24
- attr_reader :app_id
25
-
26
- # Returns the custom URL of the player these stats belong to
27
- #
28
- # @return [String] The custom URL of the player
29
- attr_reader :custom_url
30
-
31
- # Returns the friendly name of the game these stats belong to
32
- #
33
- # @return [String ]The frienldy name of the game
34
- attr_reader :game_friendly_name
19
+ include XMLData
35
20
 
36
- # Returns the full name of the game these stats belong to
21
+ # Returns the game these stats belong to
37
22
  #
38
- # @return [String] The name of the game
39
- attr_reader :game_name
23
+ # @return [SteamGame] The game object
24
+ attr_reader :game
40
25
 
41
26
  # Returns the number of hours this game has been played by the player
42
27
  #
@@ -48,10 +33,26 @@ class GameStats
48
33
  # @return [String] The privacy setting of the Steam ID
49
34
  attr_reader :privacy_state
50
35
 
51
- # Returns the 64bit numeric SteamID of the player these stats belong to
36
+ # Returns the Steam ID of the player these stats belong to
52
37
  #
53
- # @return [Fixnum] The 64bit numeric SteamID of the player
54
- attr_reader :steam_id64
38
+ # @return [SteamId] The Steam ID instance of the player
39
+ attr_reader :user
40
+
41
+ # Returns the base Steam Communtiy URL for the given player and game IDs
42
+ #
43
+ # @param [Fixnum, String] user_id The 64bit SteamID or custom URL of the user
44
+ # @param [Fixnum, String] game_id The application ID or short name of the
45
+ # game
46
+ # @return The base URL used for the given stats IDs
47
+ def self.base_url(user_id, game_id)
48
+ game_url = game_id.is_a?(Fixnum) ? "appid/#{game_id}" : game_id
49
+
50
+ if user_id.is_a? Fixnum
51
+ "http://steamcommunity.com/profiles/#{user_id}/stats/#{game_url}"
52
+ else
53
+ "http://steamcommunity.com/id/#{user_id}/stats/#{game_url}"
54
+ end
55
+ end
55
56
 
56
57
  # Creates a `GameStats` (or one of its subclasses) instance for the given
57
58
  # user and game
@@ -94,31 +95,23 @@ class GameStats
94
95
  # Creates a `GameStats` object and fetches data from the Steam Community for
95
96
  # the given user and game
96
97
  #
97
- # @param [String, Fixnum] id The custom URL or the 64bit Steam ID of the
98
+ # @param [String, Fixnum] user_id The custom URL or the 64bit Steam ID of the
98
99
  # user
99
- # @param [String] game_name The friendly name of the game
100
+ # @param [String] game_id The application ID or friendly name of the game
100
101
  # @raise [SteamCondenserError] if the stats cannot be fetched
101
- def initialize(id, game_name)
102
- if id.is_a? Numeric
103
- @steam_id64 = id
104
- else
105
- @custom_url = id.downcase
106
- end
107
- @game_friendly_name = game_name
102
+ def initialize(user_id, game_id)
103
+ @xml_data = parse "#{self.class.base_url(user_id, game_id)}?xml=all"
108
104
 
109
- url = base_url + '?xml=all'
110
- @xml_data = REXML::Document.new(open(url, {:proxy => true}).read).root
105
+ @user = SteamId.new user_id, false
111
106
 
112
- error = @xml_data.elements['error']
113
- raise SteamCondenserError, error.text unless error.nil?
107
+ error = @xml_data['error']
108
+ raise SteamCondenserError, error unless error.nil?
114
109
 
115
- @privacy_state = @xml_data.elements['privacyState'].text
110
+ @privacy_state = @xml_data['privacyState']
116
111
  if public?
117
- @app_id = @xml_data.elements['game/gameLink'].text.match(/http:\/\/store.steampowered.com\/app\/([1-9][0-9]+)/)[1].to_i
118
- @custom_url = @xml_data.elements['player/customURL'].text if @custom_url.nil?
119
- @game_name = @xml_data.elements['game/gameName'].text
120
- @hours_played = @xml_data.elements['stats/hoursPlayed'].text unless @xml_data.elements['stats/hoursPlayed'].nil?
121
- @steam_id64 = @xml_data.elements['player/steamID64'].text.to_i if @steam_id64.nil?
112
+ app_id = @xml_data['game']['gameLink'].match(/http:\/\/store.steampowered.com\/app\/([1-9][0-9]+)/)[1].to_i
113
+ @game = SteamGame.new app_id, @xml_data['game']
114
+ @hours_played = @xml_data['stats']['hoursPlayed'] unless @xml_data['stats']['hoursPlayed'].nil?
122
115
  end
123
116
  end
124
117
 
@@ -132,8 +125,8 @@ class GameStats
132
125
 
133
126
  if @achievements.nil?
134
127
  @achievements = Array.new
135
- @xml_data.elements.each('achievements/achievement') do |achievement_data|
136
- @achievements << GameAchievement.new(@steam_id64, @app_id, achievement_data)
128
+ @xml_data['achievements']['achievement'].each do |achievement|
129
+ @achievements << GameAchievement.new(@user, @game, achievement)
137
130
  end
138
131
 
139
132
  @achievements_done = @achievements.reject{ |a| !a.unlocked? }.size
@@ -169,26 +162,7 @@ class GameStats
169
162
  #
170
163
  # @return [String] The base URL used for queries on these stats
171
164
  def base_url
172
- if @custom_url.nil?
173
- "http://steamcommunity.com/profiles/#{@steam_id64}/stats/#{@game_friendly_name}"
174
- else
175
- "http://steamcommunity.com/id/#{@custom_url}/stats/#{@game_friendly_name}"
176
- end
177
- end
178
-
179
- # Returns the leaderboard for this game and the given leaderboard ID or name
180
- #
181
- # @param [Fixnum, String] id The ID or name of the leaderboard to return
182
- # @return [GameLeaderboard] The matching leaderboard if available
183
- def leaderboard(id)
184
- GameLeaderboard.leaderboard @game_friendly_name, id
185
- end
186
-
187
- # Returns an array containing all of this game's leaderboards
188
- #
189
- # @return [Array<GameLeaderboard>] The leaderboards for this game
190
- def leaderboards
191
- GameLeaderboard.leaderboards @game_friendly_name
165
+ self.class.base_url @user.id, @game.id
192
166
  end
193
167
 
194
168
  # Returns whether this Steam ID is publicly accessible
@@ -26,9 +26,9 @@ module GameWeapon
26
26
 
27
27
  # Creates a new game weapon instance with the data provided
28
28
  #
29
- # @param [REXML::Element] weapon_data The data representing this weapon
29
+ # @param [Hash<String, Object>] weapon_data The data representing this weapon
30
30
  def initialize(weapon_data)
31
- @kills = weapon_data.elements['kills'].text.to_i
31
+ @kills = weapon_data['kills'].to_i
32
32
  end
33
33
 
34
34
  # Returns the average number of shots needed for a kill with this weapon
@@ -15,6 +15,11 @@ module AbstractL4DStats
15
15
  # The names of the special infected in Left4Dead
16
16
  SPECIAL_INFECTED = %w(boomer hunter smoker tank)
17
17
 
18
+ # Returns a hash of statistics for this user's most recently played game
19
+ #
20
+ # @return [Hash<String, Object>] The most recent statistics for this user
21
+ attr_reader :most_recent_game
22
+
18
23
  # Creates a new instance of statistics for both, Left4Dead and Left4Dead 2
19
24
  # parsing basic common data
20
25
  #
@@ -25,11 +30,11 @@ module AbstractL4DStats
25
30
 
26
31
  if public?
27
32
  @most_recent_game = {}
28
- if @xml_data.elements['stats/mostrecentgame'].has_elements?
29
- @most_recent_game[:difficulty] = @xml_data.elements['stats/mostrecentgame/difficulty'].text
30
- @most_recent_game[:escaped] = (@xml_data.elements['stats/mostrecentgame/bEscaped'].text == 1)
31
- @most_recent_game[:movie] = @xml_data.elements['stats/mostrecentgame/movie'].text
32
- @most_recent_game[:time_played] = @xml_data.elements['stats/mostrecentgame/time'].text
33
+ unless @xml_data['stats']['mostrecentgame'].nil?
34
+ @most_recent_game[:difficulty] = @xml_data['stats']['mostrecentgame']['difficulty']
35
+ @most_recent_game[:escaped] = (@xml_data['stats']['mostrecentgame']['bEscaped'] == 1)
36
+ @most_recent_game[:movie] = @xml_data['stats']['mostrecentgame']['movie']
37
+ @most_recent_game[:time_played] = @xml_data['stats']['mostrecentgame']['time']
33
38
  end
34
39
  end
35
40
  end
@@ -44,14 +49,14 @@ module AbstractL4DStats
44
49
 
45
50
  if @favorites.nil?
46
51
  @favorites = {}
47
- @favorites[:campaign] = @xml_data.elements['stats/favorites/campaign'].text
48
- @favorites[:campaign_percentage] = @xml_data.elements['stats/favorites/campaignpct'].text.to_i
49
- @favorites[:character] = @xml_data.elements['stats/favorites/character'].text
50
- @favorites[:character_percentage] = @xml_data.elements['stats/favorites/characterpct'].text.to_i
51
- @favorites[:level1_weapon] = @xml_data.elements['stats/favorites/weapon1'].text
52
- @favorites[:level1_weapon_percentage] = @xml_data.elements['stats/favorites/weapon1pct'].text.to_i
53
- @favorites[:level2_weapon] = @xml_data.elements['stats/favorites/weapon2'].text
54
- @favorites[:level2_weapon_percentage] = @xml_data.elements['stats/favorites/weapon2pct'].text.to_i
52
+ @favorites[:campaign] = @xml_data['stats']['favorites']['campaign']
53
+ @favorites[:campaign_percentage] = @xml_data['stats']['favorites']['campaignpct'].to_i
54
+ @favorites[:character] = @xml_data['stats']['favorites']['character']
55
+ @favorites[:character_percentage] = @xml_data['stats']['favorites']['characterpct'].to_i
56
+ @favorites[:level1_weapon] = @xml_data['stats']['favorites']['weapon1']
57
+ @favorites[:level1_weapon_percentage] = @xml_data['stats']['favorites']['weapon1pct'].to_i
58
+ @favorites[:level2_weapon] = @xml_data['stats']['favorites']['weapon2']
59
+ @favorites[:level2_weapon_percentage] = @xml_data['stats']['favorites']['weapon2pct'].to_i
55
60
  end
56
61
 
57
62
  @favorites
@@ -68,15 +73,15 @@ module AbstractL4DStats
68
73
 
69
74
  if @lifetime_stats.nil?
70
75
  @lifetime_stats = {}
71
- @lifetime_stats[:finales_survived] = @xml_data.elements['stats/lifetime/finales'].text.to_i
72
- @lifetime_stats[:games_played] = @xml_data.elements['stats/lifetime/gamesplayed'].text.to_i
73
- @lifetime_stats[:infected_killed] = @xml_data.elements['stats/lifetime/infectedkilled'].text.to_i
74
- @lifetime_stats[:kills_per_hour] = @xml_data.elements['stats/lifetime/killsperhour'].text.to_f
75
- @lifetime_stats[:avg_kits_shared] = @xml_data.elements['stats/lifetime/kitsshared'].text.to_f
76
- @lifetime_stats[:avg_kits_used] = @xml_data.elements['stats/lifetime/kitsused'].text.to_f
77
- @lifetime_stats[:avg_pills_shared] = @xml_data.elements['stats/lifetime/pillsshared'].text.to_f
78
- @lifetime_stats[:avg_pills_used] = @xml_data.elements['stats/lifetime/pillsused'].text.to_f
79
- @lifetime_stats[:time_played] = @xml_data.elements['stats/lifetime/timeplayed'].text
76
+ @lifetime_stats[:finales_survived] = @xml_data['stats']['lifetime']['finales'].to_i
77
+ @lifetime_stats[:games_played] = @xml_data['stats']['lifetime']['gamesplayed'].to_i
78
+ @lifetime_stats[:infected_killed] = @xml_data['stats']['lifetime']['infectedkilled'].to_i
79
+ @lifetime_stats[:kills_per_hour] = @xml_data['stats']['lifetime']['killsperhour'].to_f
80
+ @lifetime_stats[:avg_kits_shared] = @xml_data['stats']['lifetime']['kitsshared'].to_f
81
+ @lifetime_stats[:avg_kits_used] = @xml_data['stats']['lifetime']['kitsused'].to_f
82
+ @lifetime_stats[:avg_pills_shared] = @xml_data['stats']['lifetime']['pillsshared'].to_f
83
+ @lifetime_stats[:avg_pills_used] = @xml_data['stats']['lifetime']['pillsused'].to_f
84
+ @lifetime_stats[:time_played] = @xml_data['stats']['lifetime']['timeplayed']
80
85
 
81
86
  @lifetime_stats[:finales_survived_percentage] = @lifetime_stats[:finales_survived].to_f / @lifetime_stats[:games_played]
82
87
  end
@@ -95,11 +100,11 @@ module AbstractL4DStats
95
100
 
96
101
  if @survival_stats.nil?
97
102
  @survival_stats = {}
98
- @survival_stats[:gold_medals] = @xml_data.elements['stats/survival/goldmedals'].text.to_i
99
- @survival_stats[:silver_medals] = @xml_data.elements['stats/survival/silvermedals'].text.to_i
100
- @survival_stats[:bronze_medals] = @xml_data.elements['stats/survival/bronzemedals'].text.to_i
101
- @survival_stats[:rounds_played] = @xml_data.elements['stats/survival/roundsplayed'].text.to_i
102
- @survival_stats[:best_time] = @xml_data.elements['stats/survival/besttime'].text.to_f
103
+ @survival_stats[:gold_medals] = @xml_data['stats']['survival']['goldmedals'].to_i
104
+ @survival_stats[:silver_medals] = @xml_data['stats']['survival']['silvermedals'].to_i
105
+ @survival_stats[:bronze_medals] = @xml_data['stats']['survival']['bronzemedals'].to_i
106
+ @survival_stats[:rounds_played] = @xml_data['stats']['survival']['roundsplayed'].to_i
107
+ @survival_stats[:best_time] = @xml_data['stats']['survival']['besttime'].to_f
103
108
  end
104
109
 
105
110
  @survival_stats
@@ -116,17 +121,17 @@ module AbstractL4DStats
116
121
 
117
122
  if @teamplay_stats.nil?
118
123
  @teamplay_stats = {}
119
- @teamplay_stats[:revived] = @xml_data.elements['stats/teamplay/revived'].text.to_i
120
- @teamplay_stats[:most_revived_difficulty] = @xml_data.elements['stats/teamplay/reviveddiff'].text
121
- @teamplay_stats[:avg_revived] = @xml_data.elements['stats/teamplay/revivedavg'].text.to_f
122
- @teamplay_stats[:avg_was_revived] = @xml_data.elements['stats/teamplay/wasrevivedavg'].text.to_f
123
- @teamplay_stats[:protected] = @xml_data.elements['stats/teamplay/protected'].text.to_i
124
- @teamplay_stats[:most_protected_difficulty] = @xml_data.elements['stats/teamplay/protecteddiff'].text
125
- @teamplay_stats[:avg_protected] = @xml_data.elements['stats/teamplay/protectedavg'].text.to_f
126
- @teamplay_stats[:avg_was_protected] = @xml_data.elements['stats/teamplay/wasprotectedavg'].text.to_f
127
- @teamplay_stats[:friendly_fire_damage] = @xml_data.elements['stats/teamplay/ffdamage'].text.to_i
128
- @teamplay_stats[:most_friendly_fire_difficulty] = @xml_data.elements['stats/teamplay/ffdamagediff'].text
129
- @teamplay_stats[:avg_friendly_fire_damage] = @xml_data.elements['stats/teamplay/ffdamageavg'].text.to_f
124
+ @teamplay_stats[:revived] = @xml_data['stats']['teamplay']['revived'].to_i
125
+ @teamplay_stats[:most_revived_difficulty] = @xml_data['stats']['teamplay']['reviveddiff']
126
+ @teamplay_stats[:avg_revived] = @xml_data['stats']['teamplay']['revivedavg'].to_f
127
+ @teamplay_stats[:avg_was_revived] = @xml_data['stats']['teamplay']['wasrevivedavg'].to_f
128
+ @teamplay_stats[:protected] = @xml_data['stats']['teamplay']['protected'].to_i
129
+ @teamplay_stats[:most_protected_difficulty] = @xml_data['stats']['teamplay']['protecteddiff']
130
+ @teamplay_stats[:avg_protected] = @xml_data['stats']['teamplay']['protectedavg'].to_f
131
+ @teamplay_stats[:avg_was_protected] = @xml_data['stats']['teamplay']['wasprotectedavg'].to_f
132
+ @teamplay_stats[:friendly_fire_damage] = @xml_data['stats']['teamplay']['ffdamage'].to_i
133
+ @teamplay_stats[:most_friendly_fire_difficulty] = @xml_data['stats']['teamplay']['ffdamagediff']
134
+ @teamplay_stats[:avg_friendly_fire_damage] = @xml_data['stats']['teamplay']['ffdamageavg'].to_f
130
135
  end
131
136
 
132
137
  @teamplay_stats
@@ -143,22 +148,22 @@ module AbstractL4DStats
143
148
 
144
149
  if @versus_stats.nil?
145
150
  @versus_stats = {}
146
- @versus_stats[:games_played] = @xml_data.elements['stats/versus/gamesplayed'].text.to_i
147
- @versus_stats[:games_completed] = @xml_data.elements['stats/versus/gamescompleted'].text.to_i
148
- @versus_stats[:finales_survived] = @xml_data.elements['stats/versus/finales'].text.to_i
149
- @versus_stats[:points] = @xml_data.elements['stats/versus/points'].text.to_i
150
- @versus_stats[:most_points_infected] = @xml_data.elements['stats/versus/pointsas'].text
151
- @versus_stats[:games_won] = @xml_data.elements['stats/versus/gameswon'].text.to_i
152
- @versus_stats[:games_lost] = @xml_data.elements['stats/versus/gameslost'].text.to_i
153
- @versus_stats[:highest_survivor_score] = @xml_data.elements['stats/versus/survivorscore'].text.to_i
151
+ @versus_stats[:games_played] = @xml_data['stats']['versus']['gamesplayed'].to_i
152
+ @versus_stats[:games_completed] = @xml_data['stats']['versus']['gamescompleted'].to_i
153
+ @versus_stats[:finales_survived] = @xml_data['stats']['versus']['finales'].to_i
154
+ @versus_stats[:points] = @xml_data['stats']['versus']['points'].to_i
155
+ @versus_stats[:most_points_infected] = @xml_data['stats']['versus']['pointsas']
156
+ @versus_stats[:games_won] = @xml_data['stats']['versus']['gameswon'].to_i
157
+ @versus_stats[:games_lost] = @xml_data['stats']['versus']['gameslost'].to_i
158
+ @versus_stats[:highest_survivor_score] = @xml_data['stats']['versus']['survivorscore'].to_i
154
159
 
155
160
  @versus_stats[:finales_survived_percentage] = @versus_stats[:finales_survived].to_f / @versus_stats[:games_played]
156
161
 
157
162
  self.class.const_get(:SPECIAL_INFECTED).each do |infected|
158
163
  @versus_stats[infected] = {}
159
- @versus_stats[infected][:special_attacks] = @xml_data.elements["stats/versus/#{infected}special"].text.to_i
160
- @versus_stats[infected][:most_damage] = @xml_data.elements["stats/versus/#{infected}dmg"].text.to_i
161
- @versus_stats[infected]['avg_lifespan'] = @xml_data.elements["stats/versus/#{infected}lifespan"].text.to_i
164
+ @versus_stats[infected][:special_attacks] = @xml_data['stats']['versus']["#{infected}special"].to_i
165
+ @versus_stats[infected][:most_damage] = @xml_data['stats']['versus']["#{infected}dmg"].to_i
166
+ @versus_stats[infected]['avg_lifespan'] = @xml_data['stats']['versus']["#{infected}lifespan"].to_i
162
167
  end
163
168
  end
164
169
 
@@ -42,14 +42,15 @@ module AbstractL4DWeapon
42
42
  # Creates a new instance of weapon from the given XML data and parses common
43
43
  # data for both, `L4DWeapon` and `L4D2Weapon`
44
44
  #
45
- # @param [REXML::Element] weapon_data The XML data for this weapon
46
- def initialize(weapon_data)
45
+ # @param [String] weapon_name The name of this weapon
46
+ # @param [Hash<String, Object>] weapon_data The XML data for this weapon
47
+ def initialize(weapon_name, weapon_data)
47
48
  super weapon_data
48
49
 
49
- @accuracy = weapon_data.elements['accuracy'].text.to_f * 0.01
50
- @headshots_percentage = weapon_data.elements['headshots'].text.to_f * 0.01
51
- @id = weapon_data.name
52
- @shots = weapon_data.elements['shots'].text.to_i
50
+ @accuracy = weapon_data['accuracy'].to_f * 0.01
51
+ @headshots_percentage = weapon_data['headshots'].to_f * 0.01
52
+ @id = weapon_name
53
+ @shots = weapon_data['shots'].to_i
53
54
  end
54
55
 
55
56
  end
@@ -43,31 +43,31 @@ class L4D2Map < L4DMap
43
43
  # information than those for Left4Dead, e.g. the teammates and items are
44
44
  # listed.
45
45
  #
46
- # @param [REXML::Element] map_data The XML data for this map
46
+ # @param [Hash<String, Object>] map_data The XML data for this map
47
47
  def initialize(map_data)
48
- @id = map_data.elements['img'].text.match(/http:\/\/steamcommunity\.com\/public\/images\/gamestats\/550\/(.*).jpg/)[1]
49
- @name = map_data.elements['name'].text
50
- @played = (map_data.elements['hasPlayed'].text.to_i == 1)
48
+ @id = map_data['img'].match(/http:\/\/cdn\.steamcommunity\.com\/public\/images\/gamestats\/550\/(.*).jpg/)[1]
49
+ @name = map_data['name']
50
+ @played = (map_data['hasPlayed'].to_i == 1)
51
51
 
52
52
  if @played
53
- @best_time = map_data.elements['besttimemilliseconds'].text.to_f / 1000
53
+ @best_time = map_data['besttimemilliseconds'].to_f / 1000
54
54
 
55
55
  @teammates = []
56
- map_data.elements.each('teammates/steamID64') do |teammate|
57
- @teammates << SteamId.new(teammate.text, false)
56
+ map_data['teammates']['steamID64'].each do |teammate|
57
+ @teammates << SteamId.new(teammate, false)
58
58
  end
59
59
 
60
60
  @items = {}
61
61
  ITEMS.each do |item|
62
- @items[item] = map_data.elements["items_#{item}"].text.to_i
62
+ @items[item] = map_data["items_#{item}"].to_i
63
63
  end
64
64
 
65
65
  @kills = {}
66
66
  INFECTED.each do |infected|
67
- @kills[infected] = map_data.elements["kills_#{infected}"].text.to_i
67
+ @kills[infected] = map_data["kills_#{infected}"].to_i
68
68
  end
69
69
 
70
- case map_data.elements['medal'].text
70
+ case map_data['medal']
71
71
  when 'gold'
72
72
  @medal = L4D2Map::GOLD
73
73
  when 'silver'
@@ -33,10 +33,10 @@ class L4D2Stats < GameStats
33
33
  super steam_id, 'l4d2'
34
34
 
35
35
  @damage_percentages = {
36
- :melee => @xml_data.elements['stats/weapons/meleepctdmg'].text.to_f,
37
- :pistols => @xml_data.elements['stats/weapons/pistolspctdmg'].text.to_f,
38
- :rifles => @xml_data.elements['stats/weapons/bulletspctdmg'].text.to_f,
39
- :shotguns => @xml_data.elements['stats/weapons/shellspctdmg'].text.to_f
36
+ :melee => @xml_data['stats']['weapons']['meleepctdmg'].to_f,
37
+ :pistols => @xml_data['stats']['weapons']['pistolspctdmg'].to_f,
38
+ :rifles => @xml_data['stats']['weapons']['bulletspctdmg'].to_f,
39
+ :shotguns => @xml_data['stats']['weapons']['shellspctdmg'].to_f
40
40
  }
41
41
  end
42
42
 
@@ -56,9 +56,9 @@ class L4D2Stats < GameStats
56
56
 
57
57
  if @lifetime_stats.nil?
58
58
  super
59
- @lifetime_stats[:avg_adrenaline_shared] = @xml_data.elements['stats/lifetime/adrenalineshared'].text.to_f
60
- @lifetime_stats[:avg_adrenaline_used] = @xml_data.elements['stats/lifetime/adrenalineused'].text.to_f
61
- @lifetime_stats[:avg_defibrillators_used] = @xml_data.elements['stats/lifetime/defibrillatorsused'].text.to_f
59
+ @lifetime_stats[:avg_adrenaline_shared] = @xml_data['stats']['lifetime']['adrenalineshared'].to_f
60
+ @lifetime_stats[:avg_adrenaline_used] = @xml_data['stats']['lifetime']['adrenalineused'].to_f
61
+ @lifetime_stats[:avg_defibrillators_used] = @xml_data['stats']['lifetime']['defibrillatorsused'].to_f
62
62
  end
63
63
 
64
64
  @lifetime_stats
@@ -76,32 +76,32 @@ class L4D2Stats < GameStats
76
76
 
77
77
  if @scavenge_stats.nil?
78
78
  @scavenge_stats = {}
79
- @scavenge_stats[:avg_cans_per_round] = @xml_data.elements['stats/scavenge/avgcansperround'].text.to_f
80
- @scavenge_stats[:perfect_rounds] = @xml_data.elements['stats/scavenge/perfect16canrounds'].text.to_i
81
- @scavenge_stats[:rounds_lost] = @xml_data.elements['stats/scavenge/roundslost'].text.to_i
82
- @scavenge_stats[:rounds_played] = @xml_data.elements['stats/scavenge/roundsplayed'].text.to_i
83
- @scavenge_stats[:rounds_won] = @xml_data.elements['stats/scavenge/roundswon'].text.to_i
84
- @scavenge_stats[:total_cans] = @xml_data.elements['stats/scavenge/totalcans'].text.to_i
79
+ @scavenge_stats[:avg_cans_per_round] = @xml_data['stats']['scavenge']['avgcansperround'].to_f
80
+ @scavenge_stats[:perfect_rounds] = @xml_data['stats']['scavenge']['perfect16canrounds'].to_i
81
+ @scavenge_stats[:rounds_lost] = @xml_data['stats']['scavenge']['roundslost'].to_i
82
+ @scavenge_stats[:rounds_played] = @xml_data['stats']['scavenge']['roundsplayed'].to_i
83
+ @scavenge_stats[:rounds_won] = @xml_data['stats']['scavenge']['roundswon'].to_i
84
+ @scavenge_stats[:total_cans] = @xml_data['stats']['scavenge']['totalcans'].to_i
85
85
 
86
86
  @scavenge_stats[:maps] = {}
87
- @xml_data.elements.each('stats/scavenge/mapstats/map') do |map_data|
88
- map_id = map_data.elements['name'].text
87
+ @xml_data['stats']['scavenge']['mapstats']['map'].each do |map_data|
88
+ map_id = map_data['name']
89
89
  @scavenge_stats[:maps][map_id] = {}
90
- @scavenge_stats[:maps][map_id]['avg_round_score'] = map_data.elements['avgscoreperround'].text.to_i
91
- @scavenge_stats[:maps][map_id]['highest_game_score'] = map_data.elements['highgamescore'].text.to_i
92
- @scavenge_stats[:maps][map_id]['highest_round_score'] = map_data.elements['highroundscore'].text.to_i
93
- @scavenge_stats[:maps][map_id]['name'] = map_data.elements['fullname'].text
94
- @scavenge_stats[:maps][map_id]['rounds_played'] = map_data.elements['roundsplayed'].text.to_i
95
- @scavenge_stats[:maps][map_id]['rounds_won'] = map_data.elements['roundswon'].text.to_i
90
+ @scavenge_stats[:maps][map_id]['avg_round_score'] = map_data['avgscoreperround'].to_i
91
+ @scavenge_stats[:maps][map_id]['highest_game_score'] = map_data['highgamescore'].to_i
92
+ @scavenge_stats[:maps][map_id]['highest_round_score'] = map_data['highroundscore'].to_i
93
+ @scavenge_stats[:maps][map_id]['name'] = map_data['fullname']
94
+ @scavenge_stats[:maps][map_id]['rounds_played'] = map_data['roundsplayed'].to_i
95
+ @scavenge_stats[:maps][map_id]['rounds_won'] = map_data['roundswon'].to_i
96
96
  end
97
97
 
98
98
  @scavenge_stats[:infected] = {}
99
- @xml_data.elements.each('stats/scavenge/infectedstats/special') do |infected_data|
100
- infected_id = infected_data.elements['name'].text
99
+ @xml_data['stats']['scavenge']['infectedstats']['special'].each do |infected_data|
100
+ infected_id = infected_data['name']
101
101
  @scavenge_stats[:infected][infected_id] = {}
102
- @scavenge_stats[:infected][infected_id]['max_damage_per_life'] = infected_data.elements['maxdmg1life'].text.to_i
103
- @scavenge_stats[:infected][infected_id]['max_pours_interrupted'] = infected_data.elements['maxpoursinterrupted'].text.to_i
104
- @scavenge_stats[:infected][infected_id]['special_attacks'] = infected_data.elements['specialattacks'].text.to_i
102
+ @scavenge_stats[:infected][infected_id]['max_damage_per_life'] = infected_data['maxdmg1life'].to_i
103
+ @scavenge_stats[:infected][infected_id]['max_pours_interrupted'] = infected_data['maxpoursinterrupted'].to_i
104
+ @scavenge_stats[:infected][infected_id]['special_attacks'] = infected_data['specialattacks'].to_i
105
105
  end
106
106
  end
107
107
 
@@ -126,7 +126,7 @@ class L4D2Stats < GameStats
126
126
  if @survival_stats.nil?
127
127
  super
128
128
  @survival_stats[:maps] = {}
129
- @xml_data.elements.each('stats/survival/maps/map') do |map_data|
129
+ @xml_data['stats']['survival']['maps']['map'].each do |map_data|
130
130
  map = L4D2Map.new(map_data)
131
131
  @survival_stats[:maps][map.id] = map
132
132
  end
@@ -146,16 +146,16 @@ class L4D2Stats < GameStats
146
146
 
147
147
  if @weapon_stats.nil?
148
148
  @weapon_stats = {}
149
- @xml_data.elements.each('stats/weapons/*') do |weapon_data|
150
- next unless weapon_data.has_elements?
149
+ @xml_data['stats']['weapons'].each do |weapon_data|
150
+ next if weapon_data.nil?
151
151
 
152
- unless %w{bilejars molotov pipes}.include? weapon_data.name
153
- weapon = L4D2Weapon.new(weapon_data)
152
+ unless %w{bilejars molotov pipes}.include? weapon_data[0]
153
+ weapon = L4D2Weapon.new *weapon_data
154
154
  else
155
- weapon = L4DExplosive.new(weapon_data)
155
+ weapon = L4DExplosive.new *weapon_data
156
156
  end
157
157
 
158
- @weapon_stats[weapon_data.name] = weapon
158
+ @weapon_stats[weapon_data[0]] = weapon
159
159
  end
160
160
  end
161
161