chore: vollständiger Workspace-Snapshot 03.07.2026
- publish_gatekeeper.py (neues Gatekeeper-System) - 4 Premium-Artikel: Veggie Match, Berlin 1960, Wild Tiled West, Scream Park - Alle kumulierten Artikel, Scripts, Medien und Caches
This commit is contained in:
@@ -0,0 +1,93 @@
|
||||
import requests
|
||||
import xml.etree.ElementTree as ET
|
||||
import time
|
||||
import sys
|
||||
|
||||
games = [
|
||||
"Leben in Reterra",
|
||||
"UNO Teams",
|
||||
"Wer weiß denn sowas – 2nd Edition",
|
||||
"Evacuation",
|
||||
"The Game – 10 Jahre Jubiläum",
|
||||
"Monsterjäger",
|
||||
"Propolis",
|
||||
"Die weiße Burg",
|
||||
"Four Planets",
|
||||
"Scrabble Zwei in Eins",
|
||||
"Risiko",
|
||||
"Skull King",
|
||||
"Hitster Original",
|
||||
"Monopoly Harry Potter",
|
||||
"Sky Team",
|
||||
"Cabanga!",
|
||||
"Azul",
|
||||
"Lotti Karotti",
|
||||
"Tag Team",
|
||||
"Tempo, kleine Schnecke",
|
||||
"Gloomhaven: Knöpfe & Krabbler",
|
||||
"My City",
|
||||
"Dragomino",
|
||||
"Tea Garden",
|
||||
]
|
||||
|
||||
def search_bgg(name):
|
||||
"""Search BGG for a game, return (id, name) or (None, None)"""
|
||||
url = f"https://boardgamegeek.com/xmlapi2/search?query={requests.utils.quote(name)}&type=boardgame"
|
||||
try:
|
||||
resp = requests.get(url, timeout=15)
|
||||
root = ET.fromstring(resp.content)
|
||||
items = root.findall('item')
|
||||
if items:
|
||||
# Return first result
|
||||
item = items[0]
|
||||
bgg_id = item.get('id')
|
||||
bgg_name = item.find('name')
|
||||
name_val = bgg_name.get('value') if bgg_name is not None else name
|
||||
return bgg_id, name_val
|
||||
except Exception as e:
|
||||
print(f" Search error for '{name}': {e}", file=sys.stderr)
|
||||
return None, None
|
||||
|
||||
def get_weight(bgg_id):
|
||||
"""Get average weight for a BGG game ID"""
|
||||
url = f"https://boardgamegeek.com/xmlapi2/thing?id={bgg_id}&stats=1"
|
||||
try:
|
||||
resp = requests.get(url, timeout=15)
|
||||
root = ET.fromstring(resp.content)
|
||||
# Find averageweight in statistics/ratings
|
||||
avg_weight = root.find('.//averageweight')
|
||||
if avg_weight is not None and avg_weight.get('value'):
|
||||
return float(avg_weight.get('value'))
|
||||
except Exception as e:
|
||||
print(f" Weight error for ID {bgg_id}: {e}", file=sys.stderr)
|
||||
return None
|
||||
|
||||
results = []
|
||||
|
||||
for i, game in enumerate(games):
|
||||
print(f"[{i+1}/24] Searching: {game}", file=sys.stderr)
|
||||
bgg_id, found_name = search_bgg(game)
|
||||
|
||||
if bgg_id:
|
||||
time.sleep(2) # Rate limit
|
||||
weight = get_weight(bgg_id)
|
||||
if weight is not None:
|
||||
results.append((game, f"{weight:.1f}"))
|
||||
print(f" -> ID={bgg_id}, Weight={weight:.1f}", file=sys.stderr)
|
||||
else:
|
||||
results.append((game, "n/a"))
|
||||
print(f" -> ID={bgg_id}, Weight=n/a", file=sys.stderr)
|
||||
else:
|
||||
results.append((game, "n/a"))
|
||||
print(f" -> Not found", file=sys.stderr)
|
||||
|
||||
if i < len(games) - 1:
|
||||
time.sleep(2) # Rate limit between searches
|
||||
|
||||
# Print final table
|
||||
print()
|
||||
print(f"{'Spielname':<40} | {'BGG Weight':>10}")
|
||||
print("-" * 53)
|
||||
for name, weight in results:
|
||||
print(f"{name:<40} | {weight:>10}")
|
||||
|
||||
Reference in New Issue
Block a user