Initial commit for helios-fitx
This commit is contained in:
commit
68deb2301d
3 changed files with 138 additions and 0 deletions
26
README.md
Normal file
26
README.md
Normal file
|
|
@ -0,0 +1,26 @@
|
|||
# Helios FitX Skill
|
||||
|
||||
Checks occupancy (Auslastung) and forecasts for FitX studios.
|
||||
Uses unofficial FitX API.
|
||||
|
||||
## Usage
|
||||
|
||||
```bash
|
||||
python3 fitx.py <studio_name>
|
||||
```
|
||||
|
||||
Example:
|
||||
```bash
|
||||
python3 fitx.py tierpark
|
||||
```
|
||||
|
||||
## Setup
|
||||
|
||||
Requires `requests` library:
|
||||
```bash
|
||||
pip install requests
|
||||
```
|
||||
|
||||
## Output
|
||||
|
||||
Returns JSON with current occupancy percentage and forecast data.
|
||||
46
SKILL.md
Normal file
46
SKILL.md
Normal file
|
|
@ -0,0 +1,46 @@
|
|||
---
|
||||
name: fitx
|
||||
description: Check FitX gym occupancy - live utilization and weekly forecast for any FitX studio.
|
||||
---
|
||||
|
||||
# FitX Auslastung
|
||||
|
||||
Zeigt die aktuelle und prognostizierte Auslastung von FitX Studios.
|
||||
|
||||
## Script
|
||||
|
||||
```bash
|
||||
python3 skills/fitx/fitx.py [URL]
|
||||
```
|
||||
|
||||
- Ohne URL: Default ist *Berlin-Tierpark*
|
||||
- Mit URL: beliebiges FitX Studio
|
||||
|
||||
## Moritz' Studios
|
||||
|
||||
- *Standard:* Berlin-Tierpark → `https://www.fitx.de/fitnessstudios/berlin-tierpark`
|
||||
- *Bei Familie in Rostock:* Rostock-Südstadt → `https://www.fitx.de/fitnessstudios/rostock-suedstadt`
|
||||
- Andere Studios: URL von fitx.de holen (Format: `https://www.fitx.de/fitnessstudios/<stadt-name>`)
|
||||
|
||||
## Output
|
||||
|
||||
JSON mit:
|
||||
- `studio`: Name des Studios
|
||||
- `live_utilization_today`: Stundenweise Live-Auslastung (Werte 0-100, nur bis aktuelle Stunde gefüllt)
|
||||
- `forecast_week_data`: Prognose pro Wochentag, stundenweise (0-100)
|
||||
|
||||
## Interpretation
|
||||
|
||||
- 0-20: sehr leer
|
||||
- 20-40: wenig los
|
||||
- 40-60: moderat
|
||||
- 60-80: voll
|
||||
- 80-100: sehr voll
|
||||
|
||||
## Antwort-Regeln
|
||||
|
||||
- Immer angeben von welchem Studio die Daten sind
|
||||
- Live-Wert der aktuellen Stunde hervorheben
|
||||
- Wenn Moritz fragt "ist das Gym voll?" → aktuelle Live-Auslastung + Empfehlung
|
||||
- Vergleich mit Forecast möglich ("normalerweise ist es um X Uhr so voll, heute ist es ruhiger/voller")
|
||||
- Wenn kein Studio angegeben: Berlin-Tierpark verwenden (außer Kontext deutet auf Rostock)
|
||||
66
fitx.py
Normal file
66
fitx.py
Normal file
|
|
@ -0,0 +1,66 @@
|
|||
import requests
|
||||
from bs4 import BeautifulSoup
|
||||
import json
|
||||
import sys
|
||||
|
||||
|
||||
def fetch_fitx_occupancy(studio_url):
|
||||
headers = {
|
||||
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36'
|
||||
}
|
||||
|
||||
response = requests.get(studio_url, headers=headers)
|
||||
|
||||
soup = BeautifulSoup(response.content, 'html.parser')
|
||||
|
||||
# The data is hidden in a section tag with class 'studio_graph'
|
||||
graph_section = soup.find('section', class_='studio_graph')
|
||||
|
||||
if not graph_section:
|
||||
print("Could not find graph section. Check URL or website structure.")
|
||||
return
|
||||
|
||||
# Extracting raw JSON strings from attributes
|
||||
visitor_data_raw = graph_section.get('data-visitordata')
|
||||
current_day_raw = graph_section.get('data-current-day-data')
|
||||
|
||||
# Parsing JSON
|
||||
# visitor_data is usually 7 arrays (Mon-Sun), each containing 24 integers (0h-23h)
|
||||
forecast_data = json.loads(visitor_data_raw)
|
||||
|
||||
# current_day_data is an array of integers for the hours passed so far today
|
||||
live_data = json.loads(current_day_raw)
|
||||
|
||||
studio_name = soup.find('h1', class_='studio_hero__headline').get_text(strip=True)
|
||||
|
||||
# Helper function to map values to time strings
|
||||
def map_to_times(data_list):
|
||||
return {f"{i:02d}:00": value for i, value in enumerate(data_list)}
|
||||
|
||||
week_days = ["Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"]
|
||||
|
||||
# Create the forecast dictionary with time keys
|
||||
forecast_with_times = {}
|
||||
for i, day in enumerate(week_days):
|
||||
forecast_with_times[day] = map_to_times(forecast_data[i])
|
||||
|
||||
result = {
|
||||
"studio": studio_name,
|
||||
"live_utilization_today": map_to_times(live_data),
|
||||
"forecast_week_data": forecast_with_times
|
||||
}
|
||||
|
||||
return result
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
# URL defaults to Berlin Tierpark, but can be overridden via command line
|
||||
target_url = "https://www.fitx.de/fitnessstudios/berlin-tierpark"
|
||||
|
||||
if len(sys.argv) > 1:
|
||||
target_url = sys.argv[1]
|
||||
|
||||
data = fetch_fitx_occupancy(target_url)
|
||||
|
||||
if data:
|
||||
print(json.dumps(data, indent=2, ensure_ascii=False))
|
||||
Loading…
Add table
Add a link
Reference in a new issue