diff --git a/data/v2/build.py b/data/v2/build.py index 535fe51fc..fa6663f05 100644 --- a/data/v2/build.py +++ b/data/v2/build.py @@ -1907,6 +1907,7 @@ def csv_record_to_objects(info): item_id=int(info[2]) if info[2] != "" else None, ability_id=int(info[3]) if info[3] != "" else None, move_id=int(info[4]) if info[4] != "" else None, + base_form_id=int(info[5]) if info[5] != "" else None, ) build_generic((PokemonFormCondition,), "pokemon_form_conditions.csv", csv_record_to_objects) diff --git a/data/v2/csv/pokemon_form_conditions.csv b/data/v2/csv/pokemon_form_conditions.csv index 61302109e..e977ea036 100644 --- a/data/v2/csv/pokemon_form_conditions.csv +++ b/data/v2/csv/pokemon_form_conditions.csv @@ -1,224 +1,227 @@ -pokemon_form_id,form_trigger_id,trigger_item_id,trigger_ability_id,trigger_move_id -493,1,1662,, -681,4,,176, -718,1,884,, -741,2,889,, -1017,1,2102,, -10028,4,,59, -10029,4,,59, -10030,4,,59, -10038,4,,122, -10041,1,285,, -10042,1,289,, -10043,1,288,, -10044,1,277,, -10045,1,280,, -10046,1,275,, -10047,1,283,, -10048,1,287,, -10049,1,278,, -10050,1,282,, -10051,1,279,, -10052,1,281,, -10053,1,284,, -10054,1,286,, -10055,1,290,, -10056,1,276,, -10063,1,442,, -10063,1,1661,, -10064,3,444,, -10067,4,,161, -10074,6,,,547 -10075,1,563,, -10076,1,564,, -10077,1,565,, -10078,1,566,, -10079,3,681,, -10080,3,681,, -10081,3,681,, -10084,6,,,548 -10085,1,684,, -10125,4,,176, -10133,1,698,, -10134,1,699,, -10135,1,717,, -10136,1,700,, -10137,1,718,, -10138,1,695,, -10139,1,714,, -10140,1,710,, -10141,1,715,, -10142,1,711,, -10143,1,701,, -10144,1,702,, -10145,1,697,, -10146,1,709,, -10147,1,719,, -10148,1,705,, -10149,1,708,, -10150,1,703,, -10151,1,696,, -10152,1,720,, -10153,1,706,, -10154,1,704,, -10155,1,721,, -10156,1,707,, -10157,1,716,, -10158,1,722,, -10159,1,712,, -10160,1,713,, -10164,1,760,, -10165,1,761,, -10166,1,793,, -10167,1,794,, -10168,1,795,, -10169,1,796,, -10170,1,797,, -10171,1,798,, -10172,1,800,, -10173,1,801,, -10174,1,802,, -10175,1,803,, -10176,1,804,, -10177,1,805,, -10178,1,799,, -10179,1,468,, -10180,1,467,, -10188,3,806,, -10189,1,808,, -10190,1,809,, -10191,1,810,, -10192,1,811,, -10219,4,,210, -10220,1,884,, -10221,1,884,, -10222,4,,211, -10225,2,890,, -10226,2,891,, -10227,2,892,, -10229,4,,208, -10232,1,902,, -10233,1,903,, -10234,1,904,, -10235,1,905,, -10236,1,906,, -10237,1,907,, -10238,1,908,, -10239,1,909,, -10240,1,910,, -10241,1,911,, -10242,1,912,, -10243,1,913,, -10244,1,914,, -10245,1,915,, -10246,1,916,, -10247,1,917,, -10248,1,918,, -10255,4,,197, -10256,4,,197, -10257,4,,197, -10258,4,,197, -10259,4,,197, -10260,4,,197, -10261,4,,197, -10262,4,,209, -10264,4,,209, -10337,4,,161, -10340,1,884,, -10341,4,,241, -10342,4,,241, -10354,4,,248, -10356,4,,258, -10357,1,1161,, -10358,1,1162,, -10364,5,,, -10365,5,,, -10366,5,,, -10367,5,,, -10368,5,,, -10369,5,,, -10370,5,,, -10371,5,,, -10372,5,,, -10373,5,,, -10374,5,,, -10375,5,,, -10376,5,,, -10377,5,,, -10378,5,,, -10379,5,,, -10380,5,,, -10381,5,,, -10382,5,,, -10383,5,,, -10384,5,,, -10385,5,,, -10386,5,,, -10387,5,,, -10388,5,,, -10389,5,,, -10390,5,,, -10391,5,,, -10392,5,,, -10393,5,,, -10394,5,,, -10395,5,,, -10396,5,,, -10397,5,,, -10414,1,1659,, -10415,1,1660,, -10425,4,,278, -10442,1,2106,, -10443,1,2107,, -10444,1,2108,, -10445,4,,304, -10446,3,1669,, -10503,1,2233,, -10504,1,2234,, -10505,1,2235,, -10506,1,2236,, -10507,1,2237,, -10508,1,2238,, -10509,1,2239,, -10510,1,2240,, -10511,1,2243,, -10512,1,2244,, -10513,1,2245,, -10514,1,2246,, -10515,1,2247,, -10516,1,2248,, -10517,1,2249,, -10518,1,2250,, -10519,1,2251,, -10520,1,2252,, -10521,1,2253,, -10522,1,2254,, -10523,1,2255,, -10524,1,2256,, -10525,1,2257,, -10526,1,2258,, -10527,1,2259,, -10528,1,2261,, -10529,1,2262,, -10530,1,2263,, -10531,1,2264,, -10532,1,2265,, -10533,1,2266,, -10534,1,2267,, -10535,1,2268,, -10536,1,2241,, -10537,1,2242,, -10538,1,2269,, -10539,1,2270,, -10540,1,2271,, -10541,1,2272,, -10542,1,2273,, -10543,1,2273,, -10544,1,2260,, -10545,1,2274,, -10546,1,2277,, -10547,1,2276,, -10548,1,2276,, -10549,1,2276,, -10550,1,2275,, -10554,1,2270,, +pokemon_form_id,form_trigger_id,trigger_item_id,trigger_ability_id,trigger_move_id,base_form_id +493,1,1662,,, +681,4,,176,, +718,1,884,,, +741,2,889,,, +1017,1,2102,,, +10028,4,,59,, +10029,4,,59,, +10030,4,,59,, +10038,4,,122,, +10041,1,285,,, +10042,1,289,,, +10043,1,288,,, +10044,1,277,,, +10045,1,280,,, +10046,1,275,,, +10047,1,283,,, +10048,1,287,,, +10049,1,278,,, +10050,1,282,,, +10051,1,279,,, +10052,1,281,,, +10053,1,284,,, +10054,1,286,,, +10055,1,290,,, +10056,1,276,,, +10063,1,442,,, +10063,1,1661,,, +10064,3,444,,, +10067,4,,161,,555 +10074,6,,,547, +10075,1,563,,, +10076,1,564,,, +10077,1,565,,, +10078,1,566,,, +10079,3,681,,, +10080,3,681,,, +10081,3,681,,, +10084,6,,,548, +10085,1,684,,, +10125,4,,176,, +10133,1,698,,, +10134,1,699,,, +10135,1,717,,, +10136,1,700,,, +10137,1,718,,, +10138,1,695,,, +10139,1,714,,, +10140,1,710,,, +10141,1,715,,, +10142,1,711,,, +10143,1,701,,, +10144,1,702,,, +10145,1,697,,, +10146,1,709,,, +10147,1,719,,, +10148,1,705,,, +10149,1,708,,, +10150,1,703,,, +10151,1,696,,, +10152,1,720,,, +10153,1,706,,, +10154,1,704,,, +10155,1,721,,, +10156,1,707,,, +10157,1,716,,, +10158,1,722,,, +10159,1,712,,, +10160,1,713,,, +10164,1,760,,, +10165,1,761,,, +10166,1,793,,, +10167,1,794,,, +10168,1,795,,, +10169,1,796,,, +10170,1,797,,, +10171,1,798,,, +10172,1,800,,, +10173,1,801,,, +10174,1,802,,, +10175,1,803,,, +10176,1,804,,, +10177,1,805,,, +10178,1,799,,, +10179,1,468,,, +10180,1,467,,, +10188,3,806,,, +10189,1,808,,, +10190,1,809,,, +10191,1,810,,, +10192,1,811,,, +10219,4,,210,,10218 +10220,1,884,,, +10221,1,884,,, +10222,4,,211,,10220 +10222,4,,211,,10221 +10225,2,890,,, +10226,2,891,,, +10227,2,892,,, +10229,4,,208,, +10232,1,902,,, +10233,1,903,,, +10234,1,904,,, +10235,1,905,,, +10236,1,906,,, +10237,1,907,,, +10238,1,908,,, +10239,1,909,,, +10240,1,910,,, +10241,1,911,,, +10242,1,912,,, +10243,1,913,,, +10244,1,914,,, +10245,1,915,,, +10246,1,916,,, +10247,1,917,,, +10248,1,918,,, +10255,4,,197,, +10256,4,,197,, +10257,4,,197,, +10258,4,,197,, +10259,4,,197,, +10260,4,,197,, +10261,4,,197,, +10262,4,,209,,778 +10264,4,,209,,10263 +10316,1,969,,,10314 +10316,1,969,,,10315 +10337,4,,161,,10336 +10340,1,884,,, +10341,4,,241,, +10342,4,,241,, +10354,4,,248,, +10356,4,,258,, +10357,1,1161,,, +10358,1,1162,,, +10364,5,,,, +10365,5,,,, +10366,5,,,, +10367,5,,,, +10368,5,,,, +10369,5,,,, +10370,5,,,, +10371,5,,,, +10372,5,,,, +10373,5,,,, +10374,5,,,, +10375,5,,,, +10376,5,,,, +10377,5,,,, +10378,5,,,, +10379,5,,,, +10380,5,,,, +10381,5,,,, +10382,5,,,, +10383,5,,,, +10384,5,,,, +10385,5,,,, +10386,5,,,, +10387,5,,,, +10388,5,,,,849 +10389,5,,,, +10390,5,,,, +10391,5,,,, +10392,5,,,, +10393,5,,,, +10394,5,,,, +10395,5,,,,892 +10396,5,,,,10360 +10397,5,,,,10343 +10414,1,1659,,, +10415,1,1660,,, +10425,4,,278,, +10442,1,2106,,, +10443,1,2107,,, +10444,1,2108,,, +10445,4,,304,, +10446,3,1669,,, +10503,1,2233,,, +10504,1,2234,,, +10505,1,2235,,, +10506,1,2236,,, +10507,1,2237,,, +10508,1,2238,,, +10509,1,2239,,, +10510,1,2240,,, +10511,1,2243,,, +10512,1,2244,,, +10513,1,2245,,, +10514,1,2246,,, +10515,1,2247,,, +10516,1,2248,,, +10517,1,2249,,, +10518,1,2250,,, +10519,1,2251,,, +10520,1,2252,,, +10521,1,2253,,,10163 +10522,1,2254,,, +10523,1,2255,,, +10524,1,2256,,, +10525,1,2257,,, +10526,1,2258,,, +10527,1,2259,,, +10528,1,2261,,, +10529,1,2262,,, +10530,1,2263,,, +10531,1,2264,,, +10532,1,2265,,, +10533,1,2266,,, +10534,1,2267,,, +10535,1,2268,,, +10536,1,2241,,, +10537,1,2242,,, +10538,1,2269,,, +10539,1,2270,,,678 +10540,1,2271,,, +10541,1,2272,,, +10542,1,2273,,,801 +10543,1,2273,,,10266 +10544,1,2260,,, +10545,1,2274,,, +10546,1,2277,,, +10547,1,2276,,,978 +10548,1,2276,,,10427 +10549,1,2276,,,10428 +10550,1,2275,,, +10554,1,2270,,,10124 diff --git a/graphql/v1beta2/metadata/databases/default/tables/public_pokemon_v2_pokemonformcondition.yaml b/graphql/v1beta2/metadata/databases/default/tables/public_pokemon_v2_pokemonformcondition.yaml index 53710f6af..c3ea68e45 100644 --- a/graphql/v1beta2/metadata/databases/default/tables/public_pokemon_v2_pokemonformcondition.yaml +++ b/graphql/v1beta2/metadata/databases/default/tables/public_pokemon_v2_pokemonformcondition.yaml @@ -10,6 +10,9 @@ object_relationships: - name: ability using: foreign_key_constraint_on: ability_id + - name: base_form + using: + foreign_key_constraint_on: base_form_id - name: item using: foreign_key_constraint_on: item_id diff --git a/openapi.yml b/openapi.yml index c5e5043ec..94477bdb8 100644 --- a/openapi.yml +++ b/openapi.yml @@ -8318,6 +8318,19 @@ components: format: uri examples: - https://pokeapi.co/api/v2/item/698/ + base_form: + type: object + nullable: true + properties: + name: + type: string + examples: + - necrozma-dusk + url: + type: string + format: uri + examples: + - https://pokeapi.co/api/v2/pokemon-form/10314/ readOnly: true required: - form_name diff --git a/pokemon_v2/migrations/0032_pokemonformcondition_base_form.py b/pokemon_v2/migrations/0032_pokemonformcondition_base_form.py new file mode 100644 index 000000000..c5b5db217 --- /dev/null +++ b/pokemon_v2/migrations/0032_pokemonformcondition_base_form.py @@ -0,0 +1,22 @@ +import django.db.models.deletion +from django.db import migrations, models + + +class Migration(migrations.Migration): + dependencies = [ + ("pokemon_v2", "0031_encounterpokemondetail"), + ] + + operations = [ + migrations.AddField( + model_name="pokemonformcondition", + name="base_form", + field=models.ForeignKey( + blank=True, + null=True, + on_delete=django.db.models.deletion.CASCADE, + related_name="base_form_conditions", + to="pokemon_v2.pokemonform", + ), + ), + ] diff --git a/pokemon_v2/models.py b/pokemon_v2/models.py index 085fcb63d..a897dbcb2 100644 --- a/pokemon_v2/models.py +++ b/pokemon_v2/models.py @@ -1757,6 +1757,13 @@ class PokemonFormCondition(HasPokemonForm): item = models.ForeignKey(Item, blank=True, null=True, on_delete=models.CASCADE) ability = models.ForeignKey(Ability, blank=True, null=True, on_delete=models.CASCADE) move = models.ForeignKey(Move, blank=True, null=True, on_delete=models.CASCADE) + base_form = models.ForeignKey( + PokemonForm, + blank=True, + null=True, + related_name="base_form_conditions", + on_delete=models.CASCADE, + ) class PokemonGameIndex(HasPokemon, HasGameIndex, HasVersion): diff --git a/pokemon_v2/serializers.py b/pokemon_v2/serializers.py index f1c1a945e..a0092fac0 100644 --- a/pokemon_v2/serializers.py +++ b/pokemon_v2/serializers.py @@ -3662,10 +3662,11 @@ class PokemonFormConditionSerializer(serializers.ModelSerializer): item = ItemSummarySerializer() ability = AbilitySummarySerializer() move = MoveSummarySerializer() + base_form = PokemonFormSummarySerializer() class Meta: model = PokemonFormCondition - fields = ("trigger", "item", "ability", "move") + fields = ("trigger", "item", "ability", "move", "base_form") class PokemonFormDetailSerializer(serializers.ModelSerializer): @@ -3868,6 +3869,21 @@ def get_pokemon_form_types(self, obj): "format": "uri", "examples": ["https://pokeapi.co/api/v2/item/698/"], }, + "base_form": { + "type": "object", + "nullable": True, + "properties": { + "name": { + "type": "string", + "examples": ["necrozma-dusk"], + }, + "url": { + "type": "string", + "format": "uri", + "examples": ["https://pokeapi.co/api/v2/pokemon-form/10314/"], + }, + }, + }, }, }, } @@ -3881,11 +3897,14 @@ def get_pokemon_form_triggers_conditions(self, obj): trigger_value = condition.pop("trigger", None) if not trigger_value: continue + base_form = condition.pop("base_form", None) trigger = {"trigger": trigger_value} for value in condition.values(): if value: trigger.update(value) break + if base_form: + trigger["base_form"] = base_form triggers.append(trigger) return triggers diff --git a/pokemon_v2/tests.py b/pokemon_v2/tests.py index 3dcc92954..ada267ff1 100644 --- a/pokemon_v2/tests.py +++ b/pokemon_v2/tests.py @@ -1478,7 +1478,9 @@ def setup_pokemon_form_trigger_data(cls, name="frm trgr for pkmn frm"): return pokemon_form_trigger @classmethod - def setup_pokemon_form_condition_data(cls, pokemon_form, form_trigger=None, item=None, ability=None, move=None): + def setup_pokemon_form_condition_data( + cls, pokemon_form, form_trigger=None, item=None, ability=None, move=None, base_form=None + ): form_trigger = form_trigger or cls.setup_pokemon_form_trigger_data(name="frm trgr for pkmn frm") item = item or cls.setup_item_data(name="itm for pkmn frm") @@ -1488,6 +1490,7 @@ def setup_pokemon_form_condition_data(cls, pokemon_form, form_trigger=None, item item=item, ability=ability, move=move, + base_form=base_form, ) pokemon_form_condition.save() return pokemon_form_condition @@ -4593,6 +4596,8 @@ def test_pokemon_form_api(self): pokemon_form_sprites = self.setup_pokemon_form_sprites_data(pokemon_form) pokemon_form_type = self.setup_pokemon_form_type_data(pokemon_form) pokemon_form_condition = self.setup_pokemon_form_condition_data(pokemon_form) + base_pokemon_form = self.setup_pokemon_form_data(pokemon=pokemon, name="base pkm form for condition") + self.setup_pokemon_form_condition_data(pokemon_form, base_form=base_pokemon_form) response = self.client.get( "{}/pokemon-form/{}/".format(API_V2, pokemon_form.pk), @@ -4651,6 +4656,15 @@ def test_pokemon_form_api(self): response.data["trigger_conditions"][0]["url"], "{}{}/item/{}/".format(TEST_HOST, API_V2, pokemon_form_condition.item.pk), ) + # a condition can name the sibling form it transforms from + self.assertEqual( + response.data["trigger_conditions"][1]["base_form"]["name"], + base_pokemon_form.name, + ) + self.assertEqual( + response.data["trigger_conditions"][1]["base_form"]["url"], + "{}{}/pokemon-form/{}/".format(TEST_HOST, API_V2, base_pokemon_form.pk), + ) # Evolution test def test_evolution_trigger_api(self):