@ -12,10 +12,14 @@ from bs4 import BeautifulSoup, Tag
import re
import time
import unicodedata
import concurrent . futures
from concurrent . futures import ThreadPoolExecutor , as_completed
import logging
logger = logging . getLogger ( ' ui_feedback ' )
from db_controller import DBController # Import your DBController
def create_encounters_table ( ) :
conn = sqlite3 . connect ( ' pokemon_forms.db ' )
cursor = conn . cursor ( )
@ -227,9 +231,7 @@ def build_query_string(table_name, criteria):
return query + " AND " . join ( conditions ) , values
def save_encounter ( conn , pfic , game , location , days , times , dual_slot , static_encounter , static_encounter_count , extra_text , stars , rods , fishing , starter ) :
cursor = conn . cursor ( )
def save_encounter ( db_controller , pfic , game , location , days , times , dual_slot , static_encounter , static_encounter_count , extra_text , stars , rods , fishing , starter ) :
extra_text_str = ' ' . join ( extra_text ) if extra_text else None
stars_str = ' , ' . join ( sorted ( stars ) ) if stars else None
rods_str = ' , ' . join ( sorted ( rods ) ) if rods else None
@ -264,12 +266,10 @@ def save_encounter(conn, pfic, game, location, days, times, dual_slot, static_en
criteria [ " time " ] = None
query , values = build_query_string ( " encounters " , criteria )
# Check if an identical record already exists
cursor . execute ( query , values )
encounter = cursor . fetchone ( )
result = db_controller . execute_query ( query , values )
if encounter == None or encounter [ 0 ] == 0 :
curso r. execute ( insert_query , ( pfic , game_id , location , day , None , dual_slot , static_encounter_count ,
if not result :
db_controlle r. execute_query_with_commit ( insert_query , ( pfic , game_id , location , day , None , dual_slot , static_encounter_count ,
static_encounter , extra_text_str , stars_str , rods_str , fishing , starter ) )
logger . info ( f " New encounter added for { pfic } in { game } at { location } on { day } " )
else :
@ -281,12 +281,10 @@ def save_encounter(conn, pfic, game, location, days, times, dual_slot, static_en
criteria [ " time " ] = time
query , values = build_query_string ( " encounters " , criteria )
# Check if an identical record already exists
curso r. execute ( query , values )
result = db_controlle r. execute_query ( query , values )
encounter = cursor . fetchone ( )
if encounter == None or encounter [ 0 ] == 0 :
cursor . execute ( insert_query , ( pfic , game_id , location , None , time , dual_slot , static_encounter_count ,
if not result :
db_controller . execute_query_with_commit ( insert_query , ( pfic , game_id , location , None , time , dual_slot , static_encounter_count ,
static_encounter , extra_text_str , stars_str , rods_str , fishing , starter ) )
logger . info ( f " New encounter added for { pfic } in { game } at { location } at { time } " )
else :
@ -297,18 +295,71 @@ def save_encounter(conn, pfic, game, location, days, times, dual_slot, static_en
criteria [ " time " ] = None
query , values = build_query_string ( " encounters " , criteria )
# Check if an identical record already exists
cursor . execute ( query , values )
encounter = cursor . fetchone ( )
result = db_controller . execute_query ( query , values )
if encounter == None or encounter [ 0 ] == 0 :
curso r. execute ( insert_query , ( pfic , game_id , location , None , None , dual_slot , static_encounter_count ,
if not result :
db_controlle r. execute_query_with_commit ( insert_query , ( pfic , game_id , location , None , None , dual_slot , static_encounter_count ,
static_encounter , extra_text_str , stars_str , rods_str , fishing , starter ) )
logger . info ( f " New encounter added for { pfic } in { game } at { location } " )
else :
logger . info ( f " Identical encounter already exists for { pfic } in { game } at { location } " )
conn . commit ( )
def save_evolve_encounter ( db_controller , pfic , game , days , times , from_pfic ) :
game_id = event_system . call_sync ( ' get_game_id_for_name ' , game )
insert_query = '''
INSERT INTO evolve_encounters
( pfic , game_id , day , time , from_pfic )
VALUES ( ? , ? , ? , ? , ? )
'''
criteria = {
" pfic " : pfic ,
" game_id " : game_id ,
" day " : None ,
" time " : None ,
" from_pfic " : from_pfic
}
if len ( days ) > 0 :
for day in days :
criteria [ " day " ] = day
criteria [ " time " ] = None
query , values = build_query_string ( " evolve_encounters " , criteria )
# Check if an identical record already exists
result = db_controller . execute_query ( query , values )
if not result :
db_controller . execute_query_with_commit ( insert_query , ( pfic , game_id , day , None , from_pfic ) )
logger . info ( f " New evolve encounter added for { pfic } in { game } on { day } " )
else :
logger . info ( f " Identical evolve encounter already exists for { pfic } in { game } on { day } " )
elif len ( times ) > 0 :
for time in times :
criteria [ " day " ] = None
criteria [ " time " ] = time
query , values = build_query_string ( " evolve_encounters " , criteria )
# Check if an identical record already exists
result = db_controller . execute_query ( query , values )
if not result :
db_controller . execute_query_with_commit ( insert_query , ( pfic , game_id , None , time , from_pfic ) )
logger . info ( f " New evolve encounter added for { pfic } in { game } at { time } " )
else :
logger . info ( f " Identical evolve encounter already exists for { pfic } in { game } at { time } " )
else :
criteria [ " day " ] = None
criteria [ " time " ] = None
query , values = build_query_string ( " evolve_encounters " , criteria )
# Check if an identical record already exists
result = db_controller . execute_query ( query , values )
if not result :
db_controller . execute_query_with_commit ( insert_query , ( pfic , game_id , None , None , from_pfic ) )
logger . info ( f " New evolve encounter added for { pfic } in { game } " )
else :
logger . info ( f " Identical evolve encounter already exists for { pfic } in { game } " )
def compare_forms ( a , b ) :
if a == b :
@ -325,7 +376,7 @@ def compare_forms(a, b):
return False
def process_pokemon_for_location_data ( pfic , name , form , national_dex , default_forms , cache , conn ) :
def process_pokemon_for_location_data ( pfic , name , form , national_dex , default_forms , cache , db_controller ) :
logger . info ( f " Processing { name } { form if form else ' ' } " )
if form and name in form :
@ -349,7 +400,13 @@ def process_pokemon_for_location_data(pfic, name, form, national_dex, default_fo
if name . lower ( ) == " ho-oh " :
name = " Ho-Oh "
if form and form . lower ( ) == " female " :
if form and form . startswith ( " Female " ) :
form = form . replace ( " Female " , " " ) . strip ( )
if form and form . startswith ( " Male " ) :
form = form . replace ( " Male " , " " ) . strip ( )
if form == " " :
form = None
search_form = form
@ -358,7 +415,6 @@ def process_pokemon_for_location_data(pfic, name, form, national_dex, default_fo
" trade " ,
" time capsule " ,
" unobtainable " ,
" evolve " ,
" tradeversion " ,
" poké transfer " ,
" friend safari " ,
@ -402,36 +458,76 @@ def process_pokemon_for_location_data(pfic, name, form, national_dex, default_fo
logger . info ( f " Found in { encounter } : " )
print_encounter = False
remaining , details = extract_additional_information ( location [ " tag " ] )
routes , remaining = extract_routes ( remaining )
logger . info ( f " Routes: { routes } " )
logger . info ( f " Remaining: { remaining . strip ( ) } " )
logger . info ( f " Details: { details } " )
if " evolve " in test_location :
remaining , details = extract_additional_information ( location [ " tag " ] )
evolve_info = extract_evolve_information ( remaining , db_controller )
if evolve_info :
logger . info ( f " Evolve Info: { evolve_info } " )
save_evolve_encounter ( db_controller , pfic , encounter , details [ " days " ] , details [ " times " ] , evolve_info [ " evolve_from " ] )
else :
remaining , details = extract_additional_information ( location [ " tag " ] )
routes , remaining = extract_routes ( remaining )
logger . info ( f " Routes: { routes } " )
logger . info ( f " Remaining: { remaining . strip ( ) } " )
logger . info ( f " Details: { details } " )
if len ( details [ " times " ] ) > 0 :
logger . info ( " Stupid Data " )
for route in routes :
route_name = f " Route { route } "
save_encounter ( db_controller , pfic , encounter , route_name , details [ " days " ] , details [ " times " ] , details [ " dual_slot " ] , details [ " static_encounter " ] , details [ " static_encounter_count " ] , details [ " extra_text " ] , details [ " stars " ] , details [ " Rods " ] , details [ " Fishing " ] , details [ " starter " ] )
if len ( details [ " times " ] ) > 0 :
logger . info ( " Stupid Data " )
if remaining != " " :
remaining_locations = remaining . replace ( " and " , " , " ) . split ( " , " )
for remaining_location in remaining_locations :
if remaining_location . strip ( ) == " " :
continue
for route in routes :
route_name = f " Route { route } "
save_encounter ( conn , pfic , encounter , route_name , details [ " days " ] , details [ " times " ] , details [ " dual_slot " ] , details [ " static_encounter " ] , details [ " static_encounter_count " ] , details [ " extra_text " ] , details [ " stars " ] , details [ " Rods " ] , details [ " Fishing " ] , details [ " starter " ] )
save_encounter ( db_controller , pfic , encounter , remaining_location . strip ( ) , details [ " days " ] , details [ " times " ] , details [ " dual_slot " ] , details [ " static_encounter " ] , details [ " static_encounter_count " ] , details [ " extra_text " ] , details [ " stars " ] , details [ " Rods " ] , details [ " Fishing " ] , details [ " starter " ] )
if remaining != " " :
remaining_locations = remaining . replace ( " and " , " , " ) . split ( " , " )
for remaining_location in remaining_locations :
if remaining_location . strip ( ) == " " :
continue
def extract_evolve_information ( s : str , db_controller ) :
details = { }
if s is None or s == " " :
return details
s = s . replace ( " Evolve " , " " )
parts = s . split ( " " )
if len ( parts ) > = 1 :
target_pokemon = parts [ 0 ] . strip ( )
form = None
if " ♀ " in target_pokemon :
target_pokemon = target_pokemon . replace ( " ♀ " , " " ) . strip ( )
form = " Female "
if " ♂ " in target_pokemon :
target_pokemon = target_pokemon . replace ( " ♂ " , " " ) . strip ( )
form = None
result = db_controller . execute_query ( '''
SELECT e . from_pfic
FROM evolution_chains e
JOIN pokemon_forms pf ON pf . PFIC = e . from_pfic
WHERE pf . name = ?
''' , (target_pokemon,))
save_encounter ( conn , pfic , encounter , remaining_location . strip ( ) , details [ " days " ] , details [ " times " ] , details [ " dual_slot " ] , details [ " static_encounter " ] , details [ " static_encounter_count " ] , details [ " extra_text " ] , details [ " stars " ] , details [ " Rods " ] , details [ " Fishing " ] , details [ " starter " ] )
if result :
details [ " evolve_from " ] = result [ 0 ] [ 0 ]
return details
def update_location_information ( cache , progress_callback = None ) :
conn = create_encounters_table ( )
cursor = conn . cursor ( )
cursor . execute ( '''
SELECT pf . PFIC , pf . name , pf . form_name , pf . national_dex
FROM pokemon_forms pf
ORDER BY pf . national_dex , pf . form_name
''' )
pokemon_forms = cursor . fetchall ( )
db_controller = DBController ( ' pokemon_forms.db ' , max_connections = 20 ) # Adjust max_connections as needed
pokemon_forms = db_controller . execute_query ( '''
SELECT pf . PFIC , pf . name , pf . form_name , pf . national_dex
FROM pokemon_forms pf
ORDER BY pf . national_dex , pf . form_name
''' )
try :
with open ( ' ./DataGatherers/DefaultForms.json ' , ' r ' ) as f :
@ -439,14 +535,27 @@ def update_location_information(cache, progress_callback=None):
except FileNotFoundError :
default_forms = [ ]
for pfic , name , form , national_dex in pokemon_forms :
if progress_callback :
progress_callback ( f " Processing { name } { form if form else ' ' } " )
process_pokemon_for_location_data ( pfic , name , form , national_dex , default_forms , cache , conn )
def process_single_pokemon ( args ) :
pfic , name , form , national_dex = args
try :
process_pokemon_for_location_data ( pfic , name , form , national_dex , default_forms , cache , db_controller )
if progress_callback :
progress_callback ( f " Processed { name } { form if form else ' ' } " )
except Exception as exc :
logger . error ( f ' Error processing { name } { form } : { exc } ' )
with ThreadPoolExecutor ( max_workers = 10 ) as executor :
futures = [ executor . submit ( process_single_pokemon , form_data ) for form_data in pokemon_forms ]
for future in as_completed ( futures ) :
try :
future . result ( )
except Exception as exc :
logger . error ( f ' A task generated an exception: { exc } ' )
conn . close ( )
db_controller . close ( )
if __name__ == " __main__ " :
cache = CacheManager ( )
update_location_information ( cache )
import cProfile
def profile_update_location_information ( cache , progress_callback = None ) :
cProfile . runctx ( ' update_location_information(cache, progress_callback) ' , globals ( ) , locals ( ) , ' profile_stats ' )