Skip to content

Loader

Assembles Pokemon model instances from PokeAPI and Smogon data.

Fetching is parallelized with 20 concurrent threads (ThreadPoolExecutor). The network is only hit on a cold cache; all subsequent runs use the disk cache.

loader

Loader -- assembles Pokemon model instances from PokeAPI + Smogon data.

Responsible for: - Fetching/caching raw API data - Selecting the curated 4-move moveset - Assigning Smogon tiers - Resolving evolutionary lines

load_all

load_all(
    gen: int, force_fetch: bool = False
) -> list[Pokemon]

Load all Pokemon for a given generation. Returns a list of Pokemon instances with full stats, moves, and tier data.

Source code in pokerena/data/loader.py
def load_all(gen: int, force_fetch: bool = False) -> list[Pokemon]:
    """
    Load all Pokemon for a given generation.
    Returns a list of Pokemon instances with full stats, moves, and tier data.
    """
    from tqdm import tqdm

    tier_map = smogon.load_tiers(gen, force_fetch=force_fetch)

    # Generation dex ranges (national dex id)
    gen_ranges = {
        1: (1, 151),
        2: (1, 251),
        3: (1, 386),
        4: (1, 493),
        5: (1, 649),
        6: (1, 721),
        7: (1, 809),
        8: (1, 905),
        9: (1, 1025),
    }
    dex_start, dex_end = gen_ranges.get(gen, (1, 151))

    log.info("Fetching Pokemon list...")
    all_species = pokeapi.fetch_pokemon_list(limit=dex_end, force=force_fetch)
    species_for_gen = all_species[dex_start - 1 : dex_end]

    results: list[Pokemon | None] = [None] * len(species_for_gen)

    with tqdm(
        total=len(species_for_gen),
        unit="mon",
        desc=f"Loading Gen {gen}",
        dynamic_ncols=True,
        leave=False,
    ) as bar:
        with ThreadPoolExecutor(max_workers=_FETCH_WORKERS) as pool:
            future_to_idx = {
                pool.submit(_load_one_entry, entry["name"], tier_map, force_fetch): i
                for i, entry in enumerate(species_for_gen)
            }
            for fut in as_completed(future_to_idx):
                idx = future_to_idx[fut]
                name = species_for_gen[idx]["name"]
                bar.set_postfix_str(name, refresh=False)
                results[idx] = fut.result()
                bar.update(1)

    pokemon_list = [p for p in results if p is not None]
    log.info("Loaded %d Pokemon for Gen %d", len(pokemon_list), gen)
    return pokemon_list