Add slot index to encounter_slots
[zzz-pokedex.git] / pokedex / db / tables.py
1 # encoding: utf8
2
3 from sqlalchemy import Column, ForeignKey, MetaData, Table
4 from sqlalchemy.ext.declarative import declarative_base
5 from sqlalchemy.ext.associationproxy import association_proxy
6 from sqlalchemy.orm import backref, relation
7 from sqlalchemy.sql import and_
8 from sqlalchemy.types import *
9
10 from pokedex.db import rst
11
12 metadata = MetaData()
13 TableBase = declarative_base(metadata=metadata)
14
15 class Ability(TableBase):
16 __tablename__ = 'abilities'
17 __singlename__ = 'ability'
18 id = Column(Integer, primary_key=True, nullable=False)
19 name = Column(Unicode(24), nullable=False)
20 flavor_text = Column(Unicode(64), nullable=False)
21 effect = Column(Unicode(255), nullable=False)
22
23 class ContestCombo(TableBase):
24 __tablename__ = 'contest_combos'
25 first_move_id = Column(Integer, ForeignKey('moves.id'), primary_key=True, nullable=False, autoincrement=False)
26 second_move_id = Column(Integer, ForeignKey('moves.id'), primary_key=True, nullable=False, autoincrement=False)
27
28 class ContestEffect(TableBase):
29 __tablename__ = 'contest_effects'
30 id = Column(Integer, primary_key=True, nullable=False)
31 appeal = Column(SmallInteger, nullable=False)
32 jam = Column(SmallInteger, nullable=False)
33 flavor_text = Column(Unicode(64), nullable=False)
34 effect = Column(Unicode(255), nullable=False)
35
36 class EggGroup(TableBase):
37 __tablename__ = 'egg_groups'
38 id = Column(Integer, primary_key=True, nullable=False)
39 name = Column(Unicode(16), nullable=False)
40
41 class Encounter(TableBase):
42 """Rows in this table represent encounters with wild Pokémon. Bear with
43 me, here.
44
45 Within a given area in a given game, encounters are differentiated by the
46 "slot" they are in and the state of the game world.
47
48 What the player is doing to get an encounter, such as surfing or walking
49 through tall grass, is called terrain. Each terrain has its own set of
50 encounter slots.
51
52 Within a terrain, slots are defined primarily by rarity. Each slot can
53 also be affected by world conditions; for example, the 20% slot for walking
54 in tall grass is affected by whether a swarm is in effect in that area.
55 "Is there a swarm?" is a condition; "there is a swarm" and "there is not a
56 swarm" are the possible values of this condition.
57
58 A slot (20% walking in grass) and any appropriate world conditions (no
59 swarm) are thus enough to define a specific encounter.
60
61 Well, okay, almost: each slot actually appears twice.
62 """
63
64 __tablename__ = 'encounters'
65 id = Column(Integer, primary_key=True, nullable=False)
66 version_id = Column(Integer, ForeignKey('versions.id'), nullable=False, autoincrement=False)
67 location_area_id = Column(Integer, ForeignKey('location_areas.id'), nullable=False, autoincrement=False)
68 encounter_slot_id = Column(Integer, ForeignKey('encounter_slots.id'), nullable=False, autoincrement=False)
69 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), nullable=False, autoincrement=False)
70 min_level = Column(Integer, nullable=False, autoincrement=False)
71 max_level = Column(Integer, nullable=False, autoincrement=False)
72
73 class EncounterCondition(TableBase):
74 """Rows in this table represent varying conditions in the game world, such
75 as time of day.
76 """
77
78 __tablename__ = 'encounter_conditions'
79 id = Column(Integer, primary_key=True, nullable=False)
80 name = Column(Unicode(64), nullable=False)
81
82 class EncounterConditionValue(TableBase):
83 """Rows in this table represent possible states for a condition; for
84 example, the state of 'swarm' could be 'swarm' or 'no swarm'.
85 """
86
87 __tablename__ = 'encounter_condition_values'
88 id = Column(Integer, primary_key=True, nullable=False)
89 encounter_condition_id = Column(Integer, ForeignKey('encounter_conditions.id'), primary_key=False, nullable=False, autoincrement=False)
90 name = Column(Unicode(64), nullable=False)
91 is_default = Column(Boolean, nullable=False)
92
93 class EncounterConditionValueMap(TableBase):
94 """Maps encounters to the specific conditions under which they occur."""
95
96 __tablename__ = 'encounter_condition_value_map'
97 encounter_id = Column(Integer, ForeignKey('encounters.id'), primary_key=True, nullable=False, autoincrement=False)
98 encounter_condition_value_id = Column(Integer, ForeignKey('encounter_condition_values.id'), primary_key=True, nullable=False, autoincrement=False)
99
100 class EncounterTerrain(TableBase):
101 """Rows in this table represent ways the player can enter a wild encounter,
102 e.g., surfing, fishing, or walking through tall grass.
103 """
104
105 __tablename__ = 'encounter_terrain'
106 id = Column(Integer, primary_key=True, nullable=False)
107 name = Column(Unicode(64), nullable=False)
108
109 class EncounterSlot(TableBase):
110 """Rows in this table represent an abstract "slot" within a terrain,
111 associated with both some set of conditions and a rarity.
112
113 Note that there are two encounters per slot, so the rarities will only add
114 up to 50.
115 """
116
117 __tablename__ = 'encounter_slots'
118 id = Column(Integer, primary_key=True, nullable=False)
119 version_group_id = Column(Integer, ForeignKey('version_groups.id'), nullable=False, autoincrement=False)
120 encounter_terrain_id = Column(Integer, ForeignKey('encounter_terrain.id'), primary_key=False, nullable=False, autoincrement=False)
121 slot = Column(Integer, nullable=True)
122 rarity = Column(Integer, nullable=False)
123
124 class EncounterSlotCondition(TableBase):
125 """Lists all conditions that affect each slot."""
126
127 __tablename__ = 'encounter_slot_conditions'
128 encounter_slot_id = Column(Integer, ForeignKey('encounter_slots.id'), primary_key=True, nullable=False, autoincrement=False)
129 encounter_condition_id = Column(Integer, ForeignKey('encounter_conditions.id'), primary_key=True, nullable=False, autoincrement=False)
130
131 class EvolutionChain(TableBase):
132 __tablename__ = 'evolution_chains'
133 id = Column(Integer, primary_key=True, nullable=False)
134 growth_rate_id = Column(Integer, ForeignKey('growth_rates.id'), nullable=False)
135 steps_to_hatch = Column(Integer, nullable=False)
136 baby_trigger_item = Column(Unicode(12))
137
138 class EvolutionMethod(TableBase):
139 __tablename__ = 'evolution_methods'
140 id = Column(Integer, primary_key=True, nullable=False)
141 name = Column(Unicode(64), nullable=False)
142 description = Column(Unicode(255), nullable=False)
143
144 class Generation(TableBase):
145 __tablename__ = 'generations'
146 id = Column(Integer, primary_key=True, nullable=False)
147 main_region_id = Column(Integer, ForeignKey('regions.id'))
148 name = Column(Unicode(16), nullable=False)
149
150 class GrowthRate(TableBase):
151 """`formula` is written in LaTeX math notation."""
152 __tablename__ = 'growth_rates'
153 id = Column(Integer, primary_key=True, nullable=False)
154 name = Column(Unicode(20), nullable=False)
155 formula = Column(Unicode(500), nullable=False)
156
157 class Item(TableBase):
158 __tablename__ = 'items'
159 __singlename__ = 'item'
160 id = Column(Integer, primary_key=True, nullable=False)
161 name = Column(Unicode(16), nullable=False)
162
163 class Language(TableBase):
164 __tablename__ = 'languages'
165 id = Column(Integer, primary_key=True, nullable=False)
166 iso639 = Column(Unicode(2), nullable=False)
167 iso3166 = Column(Unicode(2), nullable=False)
168 name = Column(Unicode(16), nullable=False)
169
170 class Location(TableBase):
171 __tablename__ = 'locations'
172 __singlename__ = 'location'
173 id = Column(Integer, primary_key=True, nullable=False)
174 region_id = Column(Integer, ForeignKey('regions.id'))
175 name = Column(Unicode(64), nullable=False)
176
177 class LocationArea(TableBase):
178 __tablename__ = 'location_areas'
179 id = Column(Integer, primary_key=True, nullable=False)
180 location_id = Column(Integer, ForeignKey('locations.id'), nullable=False)
181 internal_id = Column(Integer, nullable=False)
182 name = Column(Unicode(64), nullable=True)
183
184 class LocationAreaEncounterRate(TableBase):
185 __tablename__ = 'location_area_encounter_rates'
186 location_area_id = Column(Integer, ForeignKey('location_areas.id'), primary_key=True, nullable=False, autoincrement=False)
187 encounter_type_id = Column(Integer, ForeignKey('encounter_terrain.id'), primary_key=True, nullable=False, autoincrement=False)
188 rate = Column(Integer, nullable=True)
189
190 class Machine(TableBase):
191 __tablename__ = 'machines'
192 machine_number = Column(Integer, primary_key=True, nullable=False, autoincrement=False)
193 version_group_id = Column(Integer, ForeignKey('version_groups.id'), primary_key=True, nullable=False, autoincrement=False)
194 move_id = Column(Integer, ForeignKey('moves.id'), nullable=False)
195
196 class MoveEffectCategory(TableBase):
197 __tablename__ = 'move_effect_categories'
198 id = Column(Integer, primary_key=True, nullable=False)
199 name = Column(Unicode(64), nullable=False)
200 can_affect_user = Column(Boolean, nullable=False)
201
202 class MoveEffectCategoryMap(TableBase):
203 __tablename__ = 'move_effect_category_map'
204 move_effect_id = Column(Integer, ForeignKey('move_effects.id'), primary_key=True, nullable=False)
205 move_effect_category_id = Column(Integer, ForeignKey('move_effect_categories.id'), primary_key=True, nullable=False)
206 affects_user = Column(Boolean, primary_key=True, nullable=False)
207
208 class MoveDamageClass(TableBase):
209 __tablename__ = 'move_damage_classes'
210 id = Column(Integer, primary_key=True, nullable=False)
211 name = Column(Unicode(8), nullable=False)
212 description = Column(Unicode(64), nullable=False)
213
214 class MoveEffect(TableBase):
215 __tablename__ = 'move_effects'
216 id = Column(Integer, primary_key=True, nullable=False)
217 priority = Column(SmallInteger, nullable=False)
218 short_effect = Column(Unicode(256), nullable=False)
219 effect = Column(Unicode(5120), nullable=False)
220
221 class MoveFlag(TableBase):
222 __tablename__ = 'move_flags'
223 move_id = Column(Integer, ForeignKey('moves.id'), primary_key=True, nullable=False, autoincrement=False)
224 move_flag_type_id = Column(Integer, ForeignKey('move_flag_types.id'), primary_key=True, nullable=False, autoincrement=False)
225
226 class MoveFlagType(TableBase):
227 __tablename__ = 'move_flag_types'
228 id = Column(Integer, primary_key=True, nullable=False)
229 name = Column(Unicode(32), nullable=False)
230 description = Column(rst.RstTextColumn(128), nullable=False)
231
232 class MoveFlavorText(TableBase):
233 __tablename__ = 'move_flavor_text'
234 move_id = Column(Integer, ForeignKey('moves.id'), primary_key=True, nullable=False, autoincrement=False)
235 generation_id = Column(Integer, ForeignKey('generations.id'), primary_key=True, nullable=False, autoincrement=False)
236 flavor_text = Column(Unicode(255), nullable=False)
237
238 class MoveName(TableBase):
239 __tablename__ = 'move_names'
240 move_id = Column(Integer, ForeignKey('moves.id'), primary_key=True, nullable=False, autoincrement=False)
241 language_id = Column(Integer, ForeignKey('languages.id'), primary_key=True, nullable=False, autoincrement=False)
242 name = Column(Unicode(16), nullable=False)
243
244 class MoveTarget(TableBase):
245 __tablename__ = 'move_targets'
246 id = Column(Integer, primary_key=True, nullable=False)
247 name = Column(Unicode(32), nullable=False)
248 description = Column(Unicode(128), nullable=False)
249
250 class Move(TableBase):
251 __tablename__ = 'moves'
252 __singlename__ = 'move'
253 id = Column(Integer, primary_key=True, nullable=False)
254 name = Column(Unicode(12), nullable=False)
255 generation_id = Column(Integer, ForeignKey('generations.id'), nullable=False)
256 type_id = Column(Integer, ForeignKey('types.id'), nullable=False)
257 power = Column(SmallInteger)
258 pp = Column(SmallInteger, nullable=False)
259 accuracy = Column(SmallInteger)
260 target_id = Column(Integer, ForeignKey('move_targets.id'), nullable=False)
261 damage_class_id = Column(Integer, ForeignKey('move_damage_classes.id'), nullable=False)
262 effect_id = Column(Integer, ForeignKey('move_effects.id'), nullable=False)
263 effect_chance = Column(Integer)
264 contest_type = Column(Unicode(8), nullable=False)
265 contest_effect_id = Column(Integer, ForeignKey('contest_effects.id'), nullable=True)
266 super_contest_effect_id = Column(Integer, ForeignKey('super_contest_effects.id'), nullable=False)
267
268 class Nature(TableBase):
269 __tablename__ = 'natures'
270 id = Column(Integer, primary_key=True, nullable=False)
271 name = Column(Unicode(8), nullable=False)
272 decreased_stat_id = Column(Integer, ForeignKey('stats.id'), nullable=False)
273 increased_stat_id = Column(Integer, ForeignKey('stats.id'), nullable=False)
274
275 class Pokedex(TableBase):
276 __tablename__ = 'pokedexes'
277 id = Column(Integer, primary_key=True, nullable=False)
278 name = Column(Unicode(16), nullable=False)
279 description = Column(Unicode(512))
280
281 class PokedexVersionGroup(TableBase):
282 __tablename__ = 'pokedex_version_groups'
283 pokedex_id = Column(Integer, ForeignKey('pokedexes.id'), primary_key=True, nullable=False, autoincrement=False)
284 version_group_id = Column(Integer, ForeignKey('version_groups.id'), primary_key=True, nullable=False, autoincrement=False)
285
286 class Pokemon(TableBase):
287 """The core to this whole mess.
288
289 Note that I use both 'forme' and 'form' in both code and the database. I
290 only use 'forme' when specifically referring to Pokémon that have multiple
291 distinct species as forms—i.e., different stats or movesets. 'Form' is a
292 more general term referring to any variation within a species, including
293 purely cosmetic forms like Unown.
294 """
295 __tablename__ = 'pokemon'
296 __singlename__ = 'pokemon'
297 id = Column(Integer, primary_key=True, nullable=False)
298 name = Column(Unicode(20), nullable=False)
299 forme_name = Column(Unicode(16))
300 forme_base_pokemon_id = Column(Integer, ForeignKey('pokemon.id'))
301 generation_id = Column(Integer, ForeignKey('generations.id'))
302 evolution_chain_id = Column(Integer, ForeignKey('evolution_chains.id'))
303 evolution_parent_pokemon_id = Column(Integer, ForeignKey('pokemon.id'))
304 evolution_method_id = Column(Integer, ForeignKey('evolution_methods.id'))
305 evolution_parameter = Column(Unicode(32))
306 height = Column(Integer, nullable=False)
307 weight = Column(Integer, nullable=False)
308 species = Column(Unicode(16), nullable=False)
309 color_id = Column(Integer, ForeignKey('pokemon_colors.id'), nullable=False)
310 pokemon_shape_id = Column(Integer, ForeignKey('pokemon_shapes.id'), nullable=False)
311 habitat_id = Column(Integer, ForeignKey('pokemon_habitats.id'), nullable=True)
312 gender_rate = Column(Integer, nullable=False)
313 capture_rate = Column(Integer, nullable=False)
314 base_experience = Column(Integer, nullable=False)
315 base_happiness = Column(Integer, nullable=False)
316 is_baby = Column(Boolean, nullable=False)
317 has_gen4_fem_sprite = Column(Boolean, nullable=False)
318 has_gen4_fem_back_sprite = Column(Boolean, nullable=False)
319
320 ### Stuff to handle alternate Pokémon forms
321
322 @property
323 def national_id(self):
324 """Returns the National Pokédex number for this Pokémon. Use this
325 instead of the id directly; alternate formes may make the id incorrect.
326 """
327
328 if self.forme_base_pokemon_id:
329 return self.forme_base_pokemon_id
330 return self.id
331
332 @property
333 def full_name(self):
334 """Returns the name of this Pokémon, including its Forme, if any."""
335
336 if self.forme_name:
337 return "%s %s" % (self.forme_name.title(), self.name)
338 return self.name
339
340 @property
341 def normal_form(self):
342 """Returns the normal form for this Pokémon; i.e., this will return
343 regular Deoxys when called on any Deoxys form.
344 """
345
346 if self.forme_base_pokemon:
347 return self.forme_base_pokemon
348
349 return self
350
351 class PokemonAbility(TableBase):
352 __tablename__ = 'pokemon_abilities'
353 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
354 ability_id = Column(Integer, ForeignKey('abilities.id'), nullable=False)
355 slot = Column(Integer, primary_key=True, nullable=False, autoincrement=False)
356
357 class PokemonColor(TableBase):
358 __tablename__ = 'pokemon_colors'
359 id = Column(Integer, primary_key=True, nullable=False, autoincrement=False)
360 name = Column(Unicode(6), nullable=False)
361
362 class PokemonDexNumber(TableBase):
363 __tablename__ = 'pokemon_dex_numbers'
364 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
365 pokedex_id = Column(Integer, ForeignKey('pokedexes.id'), primary_key=True, nullable=False, autoincrement=False)
366 pokedex_number = Column(Integer, nullable=False)
367
368 class PokemonEggGroup(TableBase):
369 __tablename__ = 'pokemon_egg_groups'
370 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
371 egg_group_id = Column(Integer, ForeignKey('egg_groups.id'), primary_key=True, nullable=False, autoincrement=False)
372
373 class PokemonFlavorText(TableBase):
374 __tablename__ = 'pokemon_flavor_text'
375 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
376 version_id = Column(Integer, ForeignKey('versions.id'), primary_key=True, nullable=False, autoincrement=False)
377 flavor_text = Column(Unicode(255), nullable=False)
378
379 class PokemonFormGroup(TableBase):
380 __tablename__ = 'pokemon_form_groups'
381 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
382 is_battle_only = Column(Boolean, nullable=False)
383 description = Column(Unicode(512), nullable=False)
384
385 class PokemonFormSprite(TableBase):
386 __tablename__ = 'pokemon_form_sprites'
387 id = Column(Integer, primary_key=True, nullable=False)
388 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
389 introduced_in_version_group_id = Column(Integer, ForeignKey('version_groups.id'), primary_key=True, nullable=False, autoincrement=False)
390 name = Column(Unicode(16), nullable=True)
391 is_default = Column(Boolean, nullable=True)
392
393 class PokemonHabitat(TableBase):
394 __tablename__ = 'pokemon_habitats'
395 id = Column(Integer, primary_key=True, nullable=False, autoincrement=False)
396 name = Column(Unicode(16), nullable=False)
397
398 class PokemonItem(TableBase):
399 __tablename__ = 'pokemon_items'
400 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
401 version_id = Column(Integer, ForeignKey('versions.id'), primary_key=True, nullable=False, autoincrement=False)
402 item_id = Column(Integer, ForeignKey('items.id'), primary_key=True, nullable=False, autoincrement=False)
403 rarity = Column(Integer, nullable=False)
404
405 class PokemonMove(TableBase):
406 __tablename__ = 'pokemon_moves'
407 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
408 version_group_id = Column(Integer, ForeignKey('version_groups.id'), primary_key=True, nullable=False, autoincrement=False)
409 move_id = Column(Integer, ForeignKey('moves.id'), primary_key=True, nullable=False, autoincrement=False, index=True)
410 pokemon_move_method_id = Column(Integer, ForeignKey('pokemon_move_methods.id'), primary_key=True, nullable=False, autoincrement=False)
411 level = Column(Integer, primary_key=True, nullable=True, autoincrement=False)
412 order = Column(Integer, nullable=True)
413
414 class PokemonMoveMethod(TableBase):
415 __tablename__ = 'pokemon_move_methods'
416 id = Column(Integer, primary_key=True, nullable=False, autoincrement=False)
417 name = Column(Unicode(64), nullable=False)
418 description = Column(Unicode(255), nullable=False)
419
420 class PokemonName(TableBase):
421 __tablename__ = 'pokemon_names'
422 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
423 language_id = Column(Integer, ForeignKey('languages.id'), primary_key=True, nullable=False, autoincrement=False)
424 name = Column(Unicode(16), nullable=False)
425
426 class PokemonShape(TableBase):
427 __tablename__ = 'pokemon_shapes'
428 id = Column(Integer, primary_key=True, nullable=False)
429 name = Column(Unicode(24), nullable=False)
430 awesome_name = Column(Unicode(16), nullable=False)
431
432 class PokemonStat(TableBase):
433 __tablename__ = 'pokemon_stats'
434 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
435 stat_id = Column(Integer, ForeignKey('stats.id'), primary_key=True, nullable=False, autoincrement=False)
436 base_stat = Column(Integer, nullable=False)
437 effort = Column(Integer, nullable=False)
438
439 class PokemonType(TableBase):
440 __tablename__ = 'pokemon_types'
441 pokemon_id = Column(Integer, ForeignKey('pokemon.id'), primary_key=True, nullable=False, autoincrement=False)
442 type_id = Column(Integer, ForeignKey('types.id'), nullable=False)
443 slot = Column(Integer, primary_key=True, nullable=False, autoincrement=False)
444
445 class Region(TableBase):
446 """Major areas of the world: Kanto, Johto, etc."""
447 __tablename__ = 'regions'
448 id = Column(Integer, primary_key=True, nullable=False)
449 name = Column(Unicode(16), nullable=False)
450
451 class Stat(TableBase):
452 __tablename__ = 'stats'
453 id = Column(Integer, primary_key=True, nullable=False)
454 name = Column(Unicode(16), nullable=False)
455
456 class SuperContestCombo(TableBase):
457 __tablename__ = 'super_contest_combos'
458 first_move_id = Column(Integer, ForeignKey('moves.id'), primary_key=True, nullable=False, autoincrement=False)
459 second_move_id = Column(Integer, ForeignKey('moves.id'), primary_key=True, nullable=False, autoincrement=False)
460
461 class SuperContestEffect(TableBase):
462 __tablename__ = 'super_contest_effects'
463 id = Column(Integer, primary_key=True, nullable=False)
464 appeal = Column(SmallInteger, nullable=False)
465 flavor_text = Column(Unicode(64), nullable=False)
466
467 class TypeEfficacy(TableBase):
468 __tablename__ = 'type_efficacy'
469 damage_type_id = Column(Integer, ForeignKey('types.id'), primary_key=True, nullable=False, autoincrement=False)
470 target_type_id = Column(Integer, ForeignKey('types.id'), primary_key=True, nullable=False, autoincrement=False)
471 damage_factor = Column(Integer, nullable=False)
472
473 class Type(TableBase):
474 __tablename__ = 'types'
475 __singlename__ = 'type'
476 id = Column(Integer, primary_key=True, nullable=False)
477 name = Column(Unicode(8), nullable=False)
478 abbreviation = Column(Unicode(3), nullable=False)
479 generation_id = Column(Integer, ForeignKey('generations.id'), nullable=False)
480 damage_class_id = Column(Integer, ForeignKey('move_damage_classes.id'), nullable=False) ## ??? is none; everything else is physical or special
481
482 class VersionGroup(TableBase):
483 __tablename__ = 'version_groups'
484 id = Column(Integer, primary_key=True, nullable=False)
485 generation_id = Column(Integer, ForeignKey('generations.id'), nullable=False)
486
487 class VersionGroupRegion(TableBase):
488 __tablename__ = 'version_group_regions'
489 version_group_id = Column(Integer, ForeignKey('version_groups.id'), primary_key=True, nullable=False)
490 region_id = Column(Integer, ForeignKey('regions.id'), primary_key=True, nullable=False)
491
492 class Version(TableBase):
493 __tablename__ = 'versions'
494 id = Column(Integer, primary_key=True, nullable=False)
495 version_group_id = Column(Integer, ForeignKey('version_groups.id'), nullable=False)
496 name = Column(Unicode(32), nullable=False)
497
498
499 ### Relations down here, to avoid ordering problems
500 ContestCombo.first = relation(Move, primaryjoin=ContestCombo.first_move_id==Move.id,
501 backref='contest_combo_first')
502 ContestCombo.second = relation(Move, primaryjoin=ContestCombo.second_move_id==Move.id,
503 backref='contest_combo_second')
504
505 Encounter.location_area = relation(LocationArea, backref='encounters')
506 Encounter.pokemon = relation(Pokemon, backref='encounters')
507 Encounter.version = relation(Version, backref='encounters')
508 Encounter.slot = relation(EncounterSlot, backref='encounters')
509
510 EncounterConditionValue.condition = relation(EncounterCondition, backref='values')
511
512 Encounter.condition_value_map = relation(EncounterConditionValueMap, backref='encounter')
513 Encounter.condition_values = association_proxy('condition_value_map', 'condition_value')
514 EncounterConditionValueMap.condition_value = relation(EncounterConditionValue,
515 backref='encounter_map')
516
517 EncounterSlot.terrain = relation(EncounterTerrain, backref='slots')
518
519 EncounterSlot.condition_map = relation(EncounterSlotCondition, backref='slot')
520 EncounterSlot.conditions = association_proxy('condition_map', 'condition')
521 EncounterSlotCondition.condition = relation(EncounterCondition,
522 backref='slot_map')
523
524 EvolutionChain.growth_rate = relation(GrowthRate, backref='evolution_chains')
525
526 Generation.versions = relation(Version, secondary=VersionGroup.__table__)
527 Generation.main_region = relation(Region)
528
529 Location.region = relation(Region, backref='locations')
530
531 LocationArea.location = relation(Location, backref='areas')
532
533 Machine.version_group = relation(VersionGroup)
534
535 Move.contest_effect = relation(ContestEffect, backref='moves')
536 Move.contest_combo_next = association_proxy('contest_combo_first', 'second')
537 Move.contest_combo_prev = association_proxy('contest_combo_second', 'first')
538 Move.damage_class = relation(MoveDamageClass, backref='moves')
539 Move.flags = association_proxy('move_flags', 'flag')
540 Move.flavor_text = relation(MoveFlavorText, order_by=MoveFlavorText.generation_id, backref='move')
541 Move.foreign_names = relation(MoveName, backref='pokemon')
542 Move.generation = relation(Generation, backref='moves')
543 Move.machines = relation(Machine, backref='move')
544 Move.move_effect = relation(MoveEffect, backref='moves')
545 Move.move_flags = relation(MoveFlag, backref='move')
546 Move.super_contest_effect = relation(SuperContestEffect, backref='moves')
547 Move.super_contest_combo_next = association_proxy('super_contest_combo_first', 'second')
548 Move.super_contest_combo_prev = association_proxy('super_contest_combo_second', 'first')
549 Move.target = relation(MoveTarget, backref='moves')
550 Move.type = relation(Type, backref='moves')
551
552 Move.effect = rst.MoveEffectProperty('effect')
553 Move.priority = association_proxy('move_effect', 'priority')
554 Move.short_effect = rst.MoveEffectProperty('short_effect')
555
556 MoveEffect.category_map = relation(MoveEffectCategoryMap)
557 MoveEffect.categories = association_proxy('category_map', 'category')
558 MoveEffectCategoryMap.category = relation(MoveEffectCategory)
559
560 MoveFlag.flag = relation(MoveFlagType)
561
562 MoveFlavorText.generation = relation(Generation)
563
564 MoveName.language = relation(Language)
565
566 Nature.decreased_stat = relation(Stat, primaryjoin=Nature.decreased_stat_id==Stat.id,
567 backref='decreasing_natures')
568 Nature.increased_stat = relation(Stat, primaryjoin=Nature.increased_stat_id==Stat.id,
569 backref='increasing_natures')
570
571 Pokedex.version_groups = relation(VersionGroup, secondary=PokedexVersionGroup.__table__)
572
573 Pokemon.abilities = relation(Ability, secondary=PokemonAbility.__table__,
574 order_by=PokemonAbility.slot,
575 backref='pokemon')
576 Pokemon.formes = relation(Pokemon, primaryjoin=Pokemon.id==Pokemon.forme_base_pokemon_id,
577 backref=backref('forme_base_pokemon',
578 remote_side=[Pokemon.id]))
579 Pokemon.pokemon_color = relation(PokemonColor, backref='pokemon')
580 Pokemon.color = association_proxy('pokemon_color', 'name')
581 Pokemon.dex_numbers = relation(PokemonDexNumber, backref='pokemon')
582 Pokemon.default_form_sprite = relation(PokemonFormSprite,
583 primaryjoin=and_(
584 Pokemon.id==PokemonFormSprite.pokemon_id,
585 PokemonFormSprite.is_default==True,
586 ),
587 uselist=False)
588 Pokemon.egg_groups = relation(EggGroup, secondary=PokemonEggGroup.__table__,
589 order_by=PokemonEggGroup.egg_group_id,
590 backref='pokemon')
591 Pokemon.evolution_chain = relation(EvolutionChain, backref='pokemon')
592 Pokemon.evolution_method = relation(EvolutionMethod)
593 Pokemon.evolution_children = relation(Pokemon, primaryjoin=Pokemon.id==Pokemon.evolution_parent_pokemon_id,
594 backref=backref('evolution_parent',
595 remote_side=[Pokemon.id]))
596 Pokemon.flavor_text = relation(PokemonFlavorText, order_by=PokemonFlavorText.pokemon_id, backref='pokemon')
597 Pokemon.foreign_names = relation(PokemonName, backref='pokemon')
598 Pokemon.pokemon_habitat = relation(PokemonHabitat, backref='pokemon')
599 Pokemon.habitat = association_proxy('pokemon_habitat', 'name')
600 Pokemon.items = relation(PokemonItem)
601 Pokemon.generation = relation(Generation, backref='pokemon')
602 Pokemon.shape = relation(PokemonShape, backref='pokemon')
603 Pokemon.stats = relation(PokemonStat, backref='pokemon')
604 Pokemon.types = relation(Type, secondary=PokemonType.__table__)
605
606 PokemonDexNumber.pokedex = relation(Pokedex)
607
608 PokemonFlavorText.version = relation(Version)
609
610 PokemonItem.item = relation(Item, backref='pokemon')
611 PokemonItem.version = relation(Version)
612
613 PokemonFormGroup.pokemon = relation(Pokemon, backref=backref('form_group',
614 uselist=False))
615 PokemonFormSprite.pokemon = relation(Pokemon, backref='form_sprites')
616 PokemonFormSprite.introduced_in = relation(VersionGroup)
617
618 PokemonMove.pokemon = relation(Pokemon, backref='pokemon_moves')
619 PokemonMove.version_group = relation(VersionGroup)
620 PokemonMove.machine = relation(Machine, backref='pokemon_moves',
621 primaryjoin=and_(Machine.version_group_id==PokemonMove.version_group_id,
622 Machine.move_id==PokemonMove.move_id),
623 foreign_keys=[Machine.version_group_id, Machine.move_id],
624 uselist=False)
625 PokemonMove.move = relation(Move, backref='pokemon_moves')
626 PokemonMove.method = relation(PokemonMoveMethod)
627
628 PokemonName.language = relation(Language)
629
630 PokemonStat.stat = relation(Stat)
631
632 # This is technically a has-many; Generation.main_region_id -> Region.id
633 Region.generation = relation(Generation, uselist=False)
634 Region.version_group_regions = relation(VersionGroupRegion, backref='region',
635 order_by='VersionGroupRegion.version_group_id')
636 Region.version_groups = association_proxy('version_group_regions', 'version_group')
637
638 SuperContestCombo.first = relation(Move, primaryjoin=SuperContestCombo.first_move_id==Move.id,
639 backref='super_contest_combo_first')
640 SuperContestCombo.second = relation(Move, primaryjoin=SuperContestCombo.second_move_id==Move.id,
641 backref='super_contest_combo_second')
642
643 Type.damage_efficacies = relation(TypeEfficacy,
644 primaryjoin=Type.id
645 ==TypeEfficacy.damage_type_id,
646 backref='damage_type')
647 Type.target_efficacies = relation(TypeEfficacy,
648 primaryjoin=Type.id
649 ==TypeEfficacy.target_type_id,
650 backref='target_type')
651
652 Type.generation = relation(Generation, backref='types')
653 Type.damage_class = relation(MoveDamageClass, backref='types')
654
655 Version.version_group = relation(VersionGroup, backref='versions')
656 Version.generation = association_proxy('version_group', 'generation')
657
658 VersionGroup.generation = relation(Generation, backref='version_groups')
659 VersionGroup.version_group_regions = relation(VersionGroupRegion, backref='version_group')
660 VersionGroup.regions = association_proxy('version_group_regions', 'region')