pwood-wowr 0.5.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.
@@ -0,0 +1,85 @@
1
+ $:.unshift(File.dirname(__FILE__)) unless $:.include?(File.dirname(__FILE__)) || $:.include?(File.expand_path(File.dirname(__FILE__)))
2
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
3
+
4
+ # TODO: This class requires some thought as its source is different to others
5
+ # The data source for other classes are single XML files that contain
6
+ # information relevant to the request.
7
+ # Dungeon data is stored in two large (7kb each) files.
8
+ # Even with caching this is going to be slow as the entire XML file has
9
+ # to be read in and built even for a single look-up.
10
+
11
+ module Wowr
12
+ module Classes
13
+ class Dungeon
14
+ attr_reader :id, :key, :name,
15
+ :level_minimum, :level_maximum,
16
+ :party_size, :raid,
17
+ :release, :heroic, :bosses
18
+
19
+ alias_method :to_s, :name
20
+ alias_method :to_i, :id
21
+ alias_method :max_level, :level_maximum
22
+ alias_method :min_level, :level_minimum
23
+
24
+ def initialize(elem)
25
+ @id = elem[:id].to_i
26
+ @key = elem[:key]
27
+ @level_minimum = elem[:levelMin].to_i
28
+ @level_maximum = elem[:levelMax].to_i
29
+ @party_size = elem[:partySize].to_i
30
+ @raid = (elem[:raid].to_i == 1) ? true : false
31
+ @release = elem[:release].to_i
32
+ @heroic = (elem[:hasHeroic].to_i == 1) ? true : false
33
+
34
+ # Ideally want to be able to get the boss by both ID and key
35
+ # but by using normal hash.
36
+ # After a test it seems the method below creates 2 references to an object.
37
+ @bosses = {}
38
+
39
+ (elem/:boss).each do |elem|
40
+ # TODO: Is this insane?
41
+ # After object test, appears this will be references to the same object
42
+ boss = Boss.new(elem)
43
+ @bosses[boss.id] = boss if boss.id
44
+ @bosses[boss.key] = boss if boss.key
45
+ end
46
+ end
47
+
48
+ # Add the name data from dungeonStrings.xml
49
+ def add_name_data(elem)
50
+ # puts elem.raw_string.to_yaml
51
+ @name = elem.attributes["name"]
52
+
53
+ (elem/:boss).each do |boss_elem|
54
+ id = boss_elem[:id].to_i
55
+ key = boss_elem[:key]
56
+
57
+ @bosses[id].add_name_data(boss_elem) if id
58
+ @bosses[key].add_name_data(boss_elem) if key
59
+ end
60
+ end
61
+ end
62
+
63
+
64
+ # Note Key or id can be nil
65
+ # Not both
66
+ class Boss
67
+ attr_reader :id, :key, :name, :type
68
+
69
+ alias_method :to_s, :name
70
+ alias_method :to_i, :id
71
+
72
+ def initialize(elem)
73
+ @id = elem[:id].to_i if elem[:id].to_i
74
+ @key = elem[:key] if elem[:key]
75
+ @id = @key if !elem[:id].to_i
76
+
77
+ @type = elem[:type]
78
+ end
79
+
80
+ def add_name_data(elem)
81
+ @name = elem['name']
82
+ end
83
+ end
84
+ end
85
+ end
@@ -0,0 +1,163 @@
1
+ module Wowr
2
+ module Exceptions
3
+ def self.raise_me(code, options = {})
4
+ case code
5
+ when "noCharacter"
6
+ raise CharacterNotFound.new("Character '#{options[:character_name]}' not found.")
7
+ when "belowMinLevel"
8
+ raise CharacterBelowMinLevel.new("Character '#{options[:character_name]}' is below min level (10).")
9
+ else
10
+ raise StandardError.new("The XML returned an error: #{code.to_s}")
11
+ end
12
+ end
13
+
14
+ class InvalidXML < StandardError
15
+ end
16
+
17
+ class EmptyPage < StandardError
18
+ end
19
+
20
+ class ServerDoesNotExist < StandardError
21
+ def initialize(string)
22
+ super "Server at '#{string}' did not respond."
23
+ end
24
+ end
25
+
26
+ class CharacterNameNotSet < StandardError
27
+ def initialize
28
+ super "Character name not set in options or API constructor."
29
+ end
30
+ end
31
+
32
+ class GuildNameNotSet < StandardError
33
+ def initialize
34
+ super "Guild name not set in options or API constructor."
35
+ end
36
+ end
37
+
38
+ class ArenaTeamNameNotSet < StandardError
39
+ def initialize
40
+ super "Arena team name not set."
41
+ end
42
+ end
43
+
44
+ class CookieNotSet < StandardError
45
+ def initialize
46
+ super "Cookie required for secure requests not set. Use login(username, password) to retrieve cookie."
47
+ end
48
+ end
49
+
50
+ class GuildBankNotFound < StandardError
51
+ def initialize(guild)
52
+ super "Guild bank for '#{guild}' not found, this could be due to lack of access privileges or failed login attempt."
53
+ end
54
+ end
55
+
56
+ class InvalidLoginDetails < StandardError
57
+ def initialize
58
+ super "It was not possible to login using the username and password provided."
59
+ end
60
+ end
61
+
62
+ class LoginRequiresAuthenticator < StandardError
63
+ def initialize
64
+ super "It was not possible to login using the username and password provided, because an authenticator code is required."
65
+ end
66
+ end
67
+
68
+ class LoginBroken < StandardError
69
+ def initialize
70
+ super "It was not possible to login due to a failure of login logic."
71
+ end
72
+ end
73
+
74
+ class InvalidArenaTeamSize < StandardError
75
+ end
76
+
77
+ class RealmNotSet < StandardError
78
+ def initialize
79
+ super "Realm not set in options or API constructor."
80
+ end
81
+ end
82
+
83
+ class EventNotSet < StandardError
84
+ def initialize
85
+ super "Event not set in options or API constructor."
86
+ end
87
+ end
88
+
89
+ # Search (fold)
90
+ class SearchError < StandardError
91
+ end
92
+
93
+ class InvalidSearchType < SearchError
94
+ def initialize(string)
95
+ super "'#{string}' is not a valid search type."
96
+ end
97
+ end
98
+
99
+ class NoSearchString < SearchError
100
+ def initialize
101
+ super "No search string specified or string was empty."
102
+ end
103
+ end
104
+
105
+ class ElementNotFoundError < StandardError
106
+ end
107
+
108
+ class CharacterNotFound < ElementNotFoundError
109
+ def initialize(string)
110
+ super "Character not found with name '#{string}'."
111
+ end
112
+ end
113
+
114
+ class CharacterBelowMinLevel < ElementNotFoundError
115
+ def initialize(string)
116
+ super "Character with name '#{string}' is below min level (10)."
117
+ end
118
+ end
119
+
120
+ class CharacterNoInfo < StandardError
121
+ def initialize(string)
122
+ super "Character with name '#{string}' have no informations in the armory (not logged on WoW since last armory reset)"
123
+ end
124
+ end
125
+
126
+ class ItemNotFound < ElementNotFoundError
127
+ def initialize(string)
128
+ super "Item not found with name '#{string}'."
129
+ end
130
+ end
131
+
132
+ class GuildNotFound < ElementNotFoundError
133
+ def initialize(string)
134
+ super "Guild not found with name '#{string}'."
135
+ end
136
+ end
137
+
138
+ class ArenaTeamNotFound < ElementNotFoundError
139
+ def initialize(string)
140
+ super "Arena team not found with name '#{string}'."
141
+ end
142
+ end
143
+ # (end)
144
+
145
+ class InvalidIconSize < StandardError
146
+ def initialize(array)
147
+ super "Icon size must be: #{array.keys.inspect}"
148
+ end
149
+ end
150
+
151
+ class InvalidIconType < StandardError
152
+ def initialize(array)
153
+ super "Icon type must be: #{array.keys.inspect}"
154
+ end
155
+ end
156
+
157
+ class NetworkTimeout < StandardError
158
+ def initialize(string)
159
+ super "Network timeout '#{string}'."
160
+ end
161
+ end
162
+ end
163
+ end
@@ -0,0 +1,67 @@
1
+ module Wowr
2
+ module Extensions
3
+
4
+ # Rails's cattr_ things. activesupport/lib/active_support/core_ext/class
5
+ # Really quite handy.
6
+ # Thanks Reve's Lisa Seelye
7
+ module Class #:nodoc:
8
+ def cattr_reader(*syms) #:nodoc:
9
+ syms.flatten.each do |sym|
10
+ next if sym.is_a?(Hash)
11
+ class_eval(<<-EOS, __FILE__, __LINE__)
12
+ unless defined? @@#{sym}
13
+ @@#{sym} = nil
14
+ end
15
+
16
+ def self.#{sym}
17
+ @@#{sym}
18
+ end
19
+
20
+ def #{sym}
21
+ @@#{sym}
22
+ end
23
+ EOS
24
+ end
25
+ end
26
+
27
+ def cattr_writer(*syms) #:nodoc:
28
+ options = syms.last.is_a?(Hash) ? syms.pop : {}
29
+ syms.flatten.each do |sym|
30
+ class_eval(<<-EOS, __FILE__, __LINE__)
31
+ unless defined? @@#{sym}
32
+ @@#{sym} = nil
33
+ end
34
+
35
+ def self.#{sym}=(obj)
36
+ @@#{sym} = obj
37
+ end
38
+ #{"
39
+ def #{sym}=(obj)
40
+ @@#{sym} = obj
41
+ end
42
+ " unless options[:instance_writer] == false }
43
+ EOS
44
+ end
45
+ end
46
+ def cattr_accessor(*syms) #:nodoc:
47
+ cattr_reader(*syms)
48
+ cattr_writer(*syms)
49
+ end
50
+
51
+
52
+ def stringy(sym) #:nodoc:
53
+ class_eval(<<-EOS, __FILE__, __LINE__)
54
+ def to_s
55
+ @#{sym}
56
+ end
57
+ EOS
58
+ end
59
+ end
60
+
61
+ end
62
+ end
63
+
64
+
65
+ class Class #:nodoc:
66
+ include Wowr::Extensions::Class
67
+ end
@@ -0,0 +1,39 @@
1
+ $:.unshift(File.dirname(__FILE__)) unless $:.include?(File.dirname(__FILE__)) || $:.include?(File.expand_path(File.dirname(__FILE__)))
2
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
3
+
4
+ module Wowr
5
+ module Classes
6
+
7
+ # TODO: Fix default to_s option
8
+ class Money
9
+ attr_reader :total
10
+ alias_method :to_i, :total
11
+ alias_method :to_s, :total
12
+
13
+ def initialize(total)
14
+ @total = total
15
+ end
16
+
17
+ def gold
18
+ return (@total / 10000)
19
+ end
20
+
21
+ def silver
22
+ return (@total % 10000) / 100
23
+ end
24
+
25
+ def bronze
26
+ return @total % 100
27
+ end
28
+
29
+ def +(add)
30
+ return Money.new(self.total + add.total)
31
+ end
32
+
33
+ def -(add)
34
+ return Money.new(self.total - add.total)
35
+ end
36
+ end
37
+
38
+ end
39
+ end
@@ -0,0 +1,85 @@
1
+ $:.unshift(File.dirname(__FILE__)) unless $:.include?(File.dirname(__FILE__)) || $:.include?(File.expand_path(File.dirname(__FILE__)))
2
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
3
+
4
+ require 'character.rb'
5
+
6
+ module Wowr #:nodoc:
7
+ module Classes #:nodoc:
8
+
9
+ # A player guild containing members
10
+ # Abstract
11
+ class Guild
12
+ attr_reader :name, :url, :realm
13
+ # :roster_url, :stats_url, :stats_url_escape,
14
+ alias_method :to_s, :name
15
+
16
+ def initialize(elem)
17
+ if (elem%'guildKey')
18
+ guild = (elem%'guildKey')
19
+ else
20
+ guild = elem
21
+ end
22
+
23
+ @name = guild[:name]
24
+ @url = guild[:url]
25
+ @realm = guild[:realm]
26
+ end
27
+ end
28
+
29
+ # Basic search information returned by the search.xml
30
+ # <guilds>
31
+ # <guild
32
+ # battleGroup="Ruin"
33
+ # faction="Alliance"
34
+ # factionId="0"
35
+ # name="HAND"
36
+ # realm="Stormrage"
37
+ # relevance="100"
38
+ # url="r=Stormrage&amp;n=HAND&amp;p=1"/>
39
+ # </guilds>
40
+ class SearchGuild < Guild
41
+ attr_reader :faction, :faction_id, :battle_group
42
+
43
+ def initialize(elem)
44
+ super(elem)
45
+
46
+ @battle_group = elem[:battleGroup]
47
+ @faction = elem[:faction]
48
+ @faction_id = elem[:factionId].to_i
49
+
50
+ @relevance = elem[:relevance].to_i
51
+ end
52
+ end
53
+
54
+ # Full guild data
55
+ # <guildKey factionId="0" name="HAND" nameUrl="HAND" realm="Stormrage" realmUrl="Stormrage" url="r=Stormrage&amp;n=HAND"/>
56
+ # <guildInfo>
57
+ # <guild>
58
+ # <members filterField="" filterValue="" maxPage="1" memberCount="1" page="1" sortDir="a" sortField="">
59
+ # <character class="Paladin" classId="2" gender="Male" genderId="0" level="14" name="Sturky" race="Dwarf" raceId="3" rank="0" url="r=Stormrage&amp;n=Sturky"/>
60
+ # </members>
61
+ # </guild>
62
+ # </guildInfo>
63
+ class FullGuild < Guild
64
+ attr_reader :members, :name_url, :realm_url, :member_count
65
+
66
+ def initialize(elem)
67
+ super(elem)
68
+
69
+ @name_url = elem[:nameUrl]
70
+ @realm_url = elem[:realmUrl]
71
+
72
+ # Guild/guild_id/guild_url not set for characters
73
+ if (elem%'guildInfo')
74
+ @member_count = (elem%'guildInfo'%'guild'%'members')[:memberCount].to_i || nil
75
+ @members = {}
76
+ (elem%'guildInfo'%'guild'%'members'/:character).each do |char|
77
+ # TODO: Change to search character?
78
+ members[char[:name]] = Character.new(char)
79
+ end
80
+ end
81
+ end
82
+
83
+ end
84
+ end
85
+ end
@@ -0,0 +1,188 @@
1
+ $:.unshift(File.dirname(__FILE__)) unless $:.include?(File.dirname(__FILE__)) || $:.include?(File.expand_path(File.dirname(__FILE__)))
2
+ $LOAD_PATH.unshift(File.dirname(__FILE__))
3
+
4
+ require 'item.rb'
5
+ require 'general.rb'
6
+
7
+ module Wowr
8
+ module Classes
9
+
10
+ # def get_login_status
11
+ # name = xml%'loginStatus'[:username]
12
+ # return name == "" ? nil : name
13
+ # end
14
+
15
+ class GuildBank < Guild
16
+ attr_reader :motd, :info, :money, :ranks, :bags
17
+
18
+ def initialize(elem)
19
+ super(elem%'guildKey')
20
+
21
+ @motd = (elem%'guildMessages')[:motd]
22
+ @info = (elem%'guildMessages')[:info]
23
+ @info.gsub("&#10;", "\n")
24
+
25
+ @bags = []
26
+ (elem%'bags'/:bag).each do |bag|
27
+ @bags[bag[:id].to_i] = GuildBankBag.new(bag)
28
+ end
29
+
30
+ @ranks = []
31
+ (elem%'guildRanks'/:rank).each do |rank|
32
+ @ranks[rank[:id].to_i] = rank[:name]
33
+ end
34
+ end
35
+ end
36
+
37
+ # bags now contain references to the items
38
+ # Items can be accessed from items (within Wowr::Classes::GuildBankContents)
39
+ # Or by their individual bags using bag.items
40
+ class GuildBankContents < GuildBank
41
+ attr_reader :items
42
+
43
+ def initialize(elem, api = nil)
44
+ super(elem)
45
+ @money = Money.new((elem%'guildBank')[:money].to_i)
46
+
47
+ @items = []
48
+ (elem%'items'/:item).each do |item|
49
+ @items << GuildBankItem.new(item, bags, api)
50
+ end
51
+ end
52
+ end
53
+
54
+
55
+ # Consists of multiple groups, each with 1000 entries
56
+ class GuildBankLog < GuildBank
57
+ attr_reader :entries, :group_now, :group_next, :group_prev
58
+
59
+ def initialize(elem, api = nil)
60
+ super(elem)
61
+
62
+ @entries = []
63
+ (elem%'banklogs'/:banklog).each do |entry|
64
+ @entries << GuildBankLogEntry.new(entry, self, api)
65
+ end
66
+
67
+ @group_now = (elem%'banklogs')[:now].to_i
68
+ @group_next = (elem%'banklogs')[:next].to_i
69
+ @group_prev = (elem%'banklogs')[:prev].to_i
70
+ end
71
+ end
72
+
73
+
74
+ class GuildBankBag < Item
75
+ attr_reader :viewable
76
+ attr_accessor :items
77
+
78
+ def initialize(elem, api = nil)
79
+ super(elem, api)
80
+ @viewable = (@viewable == "true")
81
+
82
+ @items = []
83
+ end
84
+ end
85
+
86
+
87
+ # Zero to 1 items
88
+ # <banklog dtab="" money="1200000" otab="" player="Quixsilver" rank="0" ts="1212595269000" type="4"/>
89
+ # <banklog dtab="" money="0" otab="0" player="Quixsilver" rank="0" ts="1212527470000" type="2">
90
+ # <item count="1" icon="inv_potion_92" id="12820" name="Winterfall Firewater" qi="1" subtype="" type="consumables"/>
91
+ # </banklog>
92
+ class GuildBankLogEntry
93
+ attr_reader :dtab, :money, :otab, :player, :rank_id, :ts, :type_id, :item, :unknown
94
+
95
+ @@types = {
96
+ 1 => 'Deposit Item',
97
+ 2 => 'Withdraw Item',
98
+ 3 => 'Move Item',
99
+ 4 => 'Deposit Money',
100
+ 5 => 'Withdraw Money',
101
+ 6 => 'Repair',
102
+ 7 => 'Move Item',
103
+ 8 => 'Withdraw Money',
104
+ 9 => 'Guild Bank Tab Purchase'
105
+ }
106
+
107
+ def initialize(elem, bank = nil, api = nil)
108
+ @bank = bank
109
+
110
+ @dtab = elem[:dtab] == "" ? nil : elem[:dtab].to_i
111
+ @otab = elem[:otab] == "" ? nil : elem[:otab].to_i
112
+ @money = Money.new(elem[:money].to_i)
113
+ @player = elem[:player]
114
+ @unknown = elem[:unknown] == "1" ? true : false
115
+ @rank_id = elem[:rank].to_i
116
+ @ts = elem[:ts].to_i # TODO: Check TS isn't overloading
117
+ @type_id = elem[:type].to_i
118
+
119
+ if (elem%'item')
120
+ @item = GuildBankLogItem.new(elem%'item', api)
121
+ end
122
+ end
123
+
124
+ def type
125
+ return @@types[@type_id]
126
+ end
127
+
128
+ def rank
129
+ @rank_id.nil? ? nil : @bank.ranks[@rank_id]
130
+ end
131
+
132
+ def origin
133
+ @otab.nil? ? nil : @bank.bags[@otab]
134
+ end
135
+
136
+ def destination
137
+ @dtab.nil? ? nil : @bank.bags[@dtab]
138
+ end
139
+
140
+ def time
141
+ return Time.at(@ts / 1000)
142
+ end
143
+ end
144
+
145
+
146
+ # Simple item that appears in Wowr::Classes::GuildBankLog entries
147
+ # <item count="1" icon="inv_potion_92" id="12820" name="Winterfall Firewater" qi="1" subtype="" type="consumables"/>
148
+ class GuildBankLogItem < Item
149
+ attr_reader :count, :qi, :subtype, :type
150
+
151
+ def initialize(elem, api = nil)
152
+ super(elem, api)
153
+ @count = elem[:count].to_i
154
+ @qi = elem[:qi].to_i
155
+ @subtype = elem[:subtype] == "" ? nil : elem[:subtype]
156
+ @type = elem[:type]
157
+ end
158
+ end
159
+
160
+
161
+ # More detailed item used in full Wowr::Classes::GuildBank
162
+ # Very close to Wowr::Classes::EquippedItem
163
+ # <item bag="0" durability="0" icon="racial_dwarf_findtreasure" id="12219" maxDurability="0" name="Unadorned Seal of Ascension" qi="1" quantity="1" randomPropertiesId="0" seed="1827537860" slot="90" subtype="" subtypeLoc="Quest" type="consumables"/>
164
+ class GuildBankItem < Item
165
+ attr_reader :bag_id, :durability, :max_durability, :qi, :quantity,
166
+ :random_properties_id, :seed, :slot, :subtype, :subtype_loc, :type
167
+
168
+ def initialize(elem, bags = nil, api = nil)
169
+ super(elem, api)
170
+
171
+ @bag_id = elem[:bag].to_i
172
+ @qi = elem[:qi].to_i
173
+ @quantity = elem[:quantity].to_i
174
+
175
+ @durability = elem[:durability].to_i
176
+ @max_durability = elem[:maxDurability].to_i
177
+ @random_properties_id = elem[:randomPropertiesId] == 0 ? nil : elem[:randomPropertiesId].to_i
178
+ @seed = elem[:seed].to_i
179
+ @slot = elem[:slot].to_i
180
+ @subtype = elem[:subtype] == "" ? nil : elem[:subtype]
181
+ @subtype_loc = elem[:subtypeLoc] == "" ? nil : elem[:subtypeLoc]
182
+ @type = elem[:type].to_i
183
+
184
+ bags[@bag_id].items << self
185
+ end
186
+ end
187
+ end
188
+ end