Files
battery-charging-optimizer/TROUBLESHOOTING_GUIDE.md
felix.zoesch 0fa03a566a feat: Major update - Battery Optimizer v3.4.0 with comprehensive fixes
## 🎯 Hauptänderungen

### Version 3.4.0 - SOC-Drift & Charging Capacity
-  Sicherheitspuffer (20-50% konfigurierbar) für untertägige SOC-Schwankungen
-  Monatliche automatische Batterie-Kalibrierung
- 🐛 SOC-Plausibilitäts-Check (filtert 65535% Spikes beim Modus-Wechsel)
- 🐛 Zeitabhängige API-Abfrage (vor/nach 14:00 Uhr)

### Neue Features
- 🔋 **Safety Buffer**: Kompensiert SOC-Drift und Eigenverbrauch
- 🔋 **Auto-Calibration**: Monatlicher Vollzyklus für SOC-Genauigkeit
- 🔋 **Spike Protection**: 4-fach Schutz gegen ungültige SOC-Werte
- 🔋 **Smart API**: Verhindert HTTP 500 Errors bei fehlenden Tomorrow-Preisen

### Dokumentation
- 📚 SOC_CALIBRATION_GUIDE.md - Umfassender Kalibrierungs-Guide
- 📚 FIX_CHARGING_CAPACITY.md - Sicherheitspuffer-Dokumentation
- 📚 FIX_SOC_SPIKE_PROBLEM.md - Spike-Protection-Lösung
- 📚 FIX_API_TIMING.md - Zeitabhängige API-Abfrage
- 📚 DIAGNOSE_LADE_PROBLEM.md - Debug-Guide

### Neue Dateien
- battery_calibration_automation.yaml - 4 Automations für Kalibrierung
- battery_calibration_input_helper.yaml - Input Helper Config
- battery_optimizer_input_helper_safety_buffer.yaml - Puffer Config
- debug_schedule.py - Umfassendes Debug-Script

### Scripts
- battery_charging_optimizer.py v3.4.0
- hastrom_flex_extended.py v1.1.0
- debug_schedule.py v1.0.0

### Fixes
- 🐛 SOC springt auf 65535% beim ESS-Modus-Wechsel → Debounce + Plausibilitäts-Check
- 🐛 API-HTTP-500 vor 14:00 → Zeitabhängige Abfrage
- 🐛 Batterie nicht bis 100% geladen → Sicherheitspuffer
- 🐛 SOC driftet ohne Vollzyklen → Automatische Kalibrierung

## 🚀 Installation

1. Input Helper erstellen (siehe battery_optimizer_input_helper_safety_buffer.yaml)
2. Automations installieren (siehe battery_calibration_automation.yaml)
3. Scripts aktualisieren (battery_charging_optimizer.py v3.4.0)
4. PyScript neu laden

## 📊 Verbesserungen

- Präzisere Ladeplanung durch Sicherheitspuffer
- Robustheit gegen SOC-Drift
- Keine API-Fehler mehr vor 14:00
- Hardware-Stopp bei 100% wird respektiert
- Bessere Batterie-Gesundheit durch regelmäßige Kalibrierung

🤖 Generated with Claude Code (claude.ai/code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-12-12 08:04:07 +01:00

651 lines
15 KiB
Markdown

# Battery Optimizer PyScript - Troubleshooting Guide
**Problem**: Battery optimizer scripts updated but not working
**Files**: battery_charging_optimizer.py v3.2.0 + hastrom_flex_extended.py v2.0
**Date**: 2025-11-20
---
## Quick Diagnostic Checklist
Run through these checks **in order** to identify the problem:
### ✅ 1. Verify Files Are Copied to Correct Location
**Location Required**: `/config/pyscript/` (not `/config/pyscripts/` - no 's'!)
**Check via SSH** or File Editor add-on:
```bash
ls -la /config/pyscript/
```
**Expected Output**:
```
battery_charging_optimizer.py
hastrom_flex_extended.py
```
**If files are missing**: Copy them to the correct location
---
### ✅ 2. Check PyScript Integration Status
**Via Home Assistant UI**:
1. Settings → Devices & Services
2. Search for "PyScript"
3. Check status - should show "Configured"
**If not installed**: Install via HACS first
**If error status**: Click for details, note the error message
---
### ✅ 3. Reload PyScript
**Via Developer Tools**:
1. Developer Tools → Services
2. Service: `pyscript.reload`
3. Click "Call Service"
**Watch for**: Error notifications in UI or logs
---
### ✅ 4. Check Home Assistant Logs Immediately After Reload
**Via UI**:
- Settings → System → Logs
- Filter for "pyscript"
**Look for these specific errors**:
#### Error Type 1: Module Import Error
```
ModuleNotFoundError: No module named 'zoneinfo'
```
**Cause**: Python 3.9+ required for zoneinfo
**Fix**: Update Home Assistant or use alternative (see Fix #1 below)
---
#### Error Type 2: Task Executor Not Defined
```
NameError: name 'task' is not defined
```
**Cause**: PyScript not fully initialized or wrong PyScript version
**Fix**: Update PyScript integration to latest version
---
#### Error Type 3: Syntax Error
```
SyntaxError: invalid syntax (line XXX)
```
**Cause**: File corruption or copy error
**Fix**: Re-copy files, ensure UTF-8 encoding
---
#### Error Type 4: Entity Not Found
```
AttributeError: 'state' object has no attribute 'input_text'
```
**Cause**: Required helper entities don't exist
**Fix**: Create missing entities (see Fix #2 below)
---
### ✅ 5. Verify Services Were Registered
**Via Developer Tools**:
1. Developer Tools → Services
2. Search for "pyscript"
**Expected Services**:
- `pyscript.calculate_charging_schedule`
- `pyscript.execute_charging_schedule`
- `pyscript.getprices_extended`
- `pyscript.reload`
**If services missing**: PyScript failed to load files - check logs
---
### ✅ 6. Test Price Fetcher First
**Manual Test**:
```yaml
service: pyscript.getprices_extended
```
**Check Results**:
1. Developer Tools → States
2. Search for: `sensor.hastrom_flex_pro_ext`
3. Check attributes for:
- `prices_today` (should be array of 24 prices)
- `prices_tomorrow` (might be empty before 14:00)
- `last_update` (should show recent timestamp)
**If entity doesn't exist**: Script failed to run - check logs
**If no data in attributes**: API call failed - check logs for HTTP errors
---
### ✅ 7. Test Optimizer
**Manual Test**:
```yaml
service: pyscript.calculate_charging_schedule
```
**Check Results**:
1. Developer Tools → States
2. Search for: `pyscript.battery_charging_schedule`
3. Check attributes for:
- `schedule` (array of hour-by-hour plan)
- `num_charges` (number of charging hours)
- `last_update` (timestamp)
**If state doesn't exist**: Optimizer failed to run completely
**If schedule is empty**: Check log for calculation errors
---
## Common Error Scenarios & Fixes
### Scenario 1: "Cannot import zoneinfo"
**Full Error**:
```
ModuleNotFoundError: No module named 'zoneinfo'
```
**Fix - Option A (Recommended)**: Update Home Assistant
- Requires HA 2021.7+ (Python 3.9+)
- Settings → System → Updates
**Fix - Option B**: Use pytz fallback
Edit both scripts, replace:
```python
from zoneinfo import ZoneInfo
TIMEZONE = ZoneInfo("Europe/Berlin")
```
With:
```python
try:
from zoneinfo import ZoneInfo
TIMEZONE = ZoneInfo("Europe/Berlin")
except ImportError:
import pytz
TIMEZONE = pytz.timezone("Europe/Berlin")
```
Then reload PyScript.
---
### Scenario 2: Missing Input Helpers
**Error**:
```
AttributeError: 'state' object has no attribute 'input_boolean'
```
**Required Entities - Input Booleans**:
- `input_boolean.battery_optimizer_enabled`
- `input_boolean.goodwe_manual_control`
- `input_boolean.battery_optimizer_manual_override`
**Required Entities - Input Numbers**:
- `input_number.battery_capacity_kwh` (default: 10)
- `input_number.battery_optimizer_min_soc` (default: 20)
- `input_number.battery_optimizer_max_soc` (default: 100)
- `input_number.battery_optimizer_max_charge_power` (default: 5000)
- `input_number.battery_optimizer_price_threshold` (default: 28)
- `input_number.battery_optimizer_reserve_capacity` (default: 2)
- `input_number.battery_optimizer_pv_threshold` (default: 500)
- `input_number.charge_power_battery`
**Required Entities - Input Text**:
- `input_text.battery_optimizer_status`
**Create via UI**:
1. Settings → Devices & Services → Helpers
2. Click "Create Helper"
3. Choose "Number" or "Toggle" or "Text"
4. Set ID exactly as shown above
**Or via configuration.yaml**:
```yaml
input_boolean:
battery_optimizer_enabled:
name: Battery Optimizer Enabled
initial: on
goodwe_manual_control:
name: GoodWe Manual Control
initial: off
battery_optimizer_manual_override:
name: Battery Optimizer Manual Override
initial: off
input_number:
battery_capacity_kwh:
name: Battery Capacity (kWh)
min: 0
max: 50
step: 0.1
initial: 10
unit_of_measurement: kWh
battery_optimizer_min_soc:
name: Min SOC
min: 0
max: 100
step: 1
initial: 20
unit_of_measurement: '%'
battery_optimizer_max_soc:
name: Max SOC
min: 0
max: 100
step: 1
initial: 100
unit_of_measurement: '%'
battery_optimizer_max_charge_power:
name: Max Charge Power
min: 0
max: 10000
step: 100
initial: 5000
unit_of_measurement: W
battery_optimizer_price_threshold:
name: Price Threshold
min: 0
max: 100
step: 0.1
initial: 28
unit_of_measurement: ct/kWh
battery_optimizer_reserve_capacity:
name: Reserve Capacity
min: 0
max: 10
step: 0.1
initial: 2
unit_of_measurement: kWh
battery_optimizer_pv_threshold:
name: PV Threshold
min: 0
max: 5000
step: 100
initial: 500
unit_of_measurement: Wh
charge_power_battery:
name: Charge Power Battery
min: 0
max: 10000
step: 100
initial: 0
unit_of_measurement: W
input_text:
battery_optimizer_status:
name: Battery Optimizer Status
initial: "Initialisiert"
max: 255
```
---
### Scenario 3: Time Triggers Not Firing
**Symptom**: Manual calls work, but automated schedule doesn't run
**Check 1**: Verify triggers are registered
```yaml
# Developer Tools → Services
service: pyscript.debug
```
Look in logs for registered triggers.
**Check 2**: Verify system time and timezone
**Fix**: Ensure Home Assistant timezone is set correctly:
```yaml
# configuration.yaml
homeassistant:
time_zone: Europe/Berlin
```
**Check 3**: PyScript might not support cron syntax used
Try alternative trigger in configuration.yaml:
```yaml
automation:
- alias: "Trigger Battery Optimizer Daily"
trigger:
- platform: time
at: "14:05:00"
action:
- service: pyscript.calculate_charging_schedule
- alias: "Execute Battery Schedule Hourly"
trigger:
- platform: time_pattern
minutes: "05"
action:
- service: pyscript.execute_charging_schedule
```
---
### Scenario 4: Sensors Not Created by hastrom_flex_extended.py
**Symptom**: Service runs without error, but sensors don't appear
**Check**: State must be set with a numeric value first
In `hastrom_flex_extended.py`, ensure lines 87 and 109 execute:
```python
state.set("sensor.hastrom_flex_ext", value=float(current_price))
state.set("sensor.hastrom_flex_pro_ext", value=float(current_price))
```
**Problem**: If `current_price` is `None`, state.set won't create entity
**Debug**: Add logging before state.set:
```python
log.info(f"Current price: {current_price}, type: {type(current_price)}")
if current_price is not None:
state.set("sensor.hastrom_flex_ext", value=float(current_price))
else:
log.error("Current price is None - sensor not created")
```
---
### Scenario 5: Schedule Executes at Wrong Time
**Symptom**: Charging starts at wrong hour (e.g., 15:00 instead of 14:00)
**Cause**: UTC/Local timezone mismatch
**Check**: What timezone does PyScript use?
Add debug logging in `execute_charging_schedule()`:
```python
now = get_local_now()
log.info(f"Current time: {now}")
log.info(f"Current hour: {now.hour}")
log.info(f"Timezone: {now.tzinfo}")
log.info(f"UTC offset: {now.utcoffset()}")
```
**Fix**: Verify `get_local_now()` returns Europe/Berlin time
- During winter: UTC+1 (CET)
- During summer: UTC+2 (CEST)
---
### Scenario 6: State Attribute Size Too Large
**Error**:
```
ValueError: State attributes exceed maximum size
```
**Cause**: Schedule with 48+ hours of detailed data
**Fix - Option A**: Reduce schedule detail
Store only charging hours, not all hours:
```python
# In save_schedule(), filter before saving
schedule_compact = [s for s in schedule if s['action'] == 'charge']
state.set(..., new_attributes={'schedule': schedule_compact, ...})
```
**Fix - Option B**: Use separate entity for each day
```python
# Save today and tomorrow separately
schedule_today = [s for s in schedule if not s.get('is_tomorrow')]
schedule_tomorrow = [s for s in schedule if s.get('is_tomorrow')]
state.set('pyscript.battery_schedule_today', ...)
state.set('pyscript.battery_schedule_tomorrow', ...)
```
---
## Advanced Debugging
### Enable PyScript Debug Logging
**configuration.yaml**:
```yaml
logger:
default: info
logs:
custom_components.pyscript: debug
custom_components.pyscript.file.battery_charging_optimizer: debug
custom_components.pyscript.file.hastrom_flex_extended: debug
```
Restart Home Assistant, then check logs.
---
### Add Comprehensive Error Handling
Edit both scripts, wrap main logic in detailed try-catch:
**battery_charging_optimizer.py**, line 38:
```python
try:
# Existing code...
except Exception as e:
log.error(f"EXCEPTION in calculate_charging_schedule: {e}")
log.error(f"Exception type: {type(e).__name__}")
import traceback
log.error(f"Traceback:\n{traceback.format_exc()}")
input_text.battery_optimizer_status = f"Error: {str(e)[:100]}"
raise # Re-raise to see in HA logs
```
---
### Manual Execution with Timing
Test each component manually and time them:
```yaml
# 1. Test price fetch (should take 1-3 seconds)
service: pyscript.getprices_extended
# Wait 5 seconds, then check logs
# 2. Test optimization (should take < 1 second)
service: pyscript.calculate_charging_schedule
# Wait 5 seconds, then check logs
# 3. Test execution (should be instant)
service: pyscript.execute_charging_schedule
# Check logs immediately
```
---
### Check for Conflicting Automations
Search for automations that might interfere:
1. Developer Tools → States
2. Filter: `automation.`
3. Look for automations controlling:
- `input_boolean.goodwe_manual_control`
- `input_number.charge_power_battery`
If other automations are modifying these, they might conflict.
---
## Expected Successful Log Output
When everything works, you should see:
**After `pyscript.getprices_extended`**:
```
Lade Preise für 20251120 und 20251121 (lokale Zeit: 2025-11-20 15:00:00 CET)
✓ API-Abfrage erfolgreich: 48 Datenpunkte
📊 haStrom FLEX PRO Extended - Preise aktualisiert:
├─ Heute: 24 Stunden
└─ Morgen: 24 Stunden (verfügbar: True)
📈 Heute: Min=18.50, Max=35.20, Avg=25.30 ct/kWh
📈 Morgen: Min=17.80, Max=34.50, Avg=24.80 ct/kWh
```
**After `pyscript.calculate_charging_schedule`**:
```
=== Batterie-Optimierung gestartet (v3.2 - FIXED Timezones) ===
Konfiguration geladen: SOC 20-100%, Max 5000W
✓ Nutze Extended-Sensor: sensor.hastrom_flex_pro_ext
Strompreise geladen: 48 Stunden (Tomorrow: True)
PV-Prognose: Heute 12.5 kWh, Morgen 8.3 kWh
Aktueller SOC: 45%
Lokale Zeit: 2025-11-20 15:00:00 CET
Planungsfenster: 45 Stunden (ab jetzt)
Preise: Min=17.80, Max=35.20, Avg=25.05 ct/kWh
Verfügbare Ladekapazität: 5.50 kWh
🎯 Benötigte Ladestunden: 2 (bei 5000W pro Stunde)
✓ Top 2 günstigste Stunden ausgewählt:
- Preise: 17.80 - 18.20 ct/kWh
- Durchschnitt: 18.00 ct/kWh
- Ersparnis vs. Durchschnitt: 7.05 ct/kWh
- Davon morgen: 1
- Zeiten: 02:00 heute (17.80ct), 03:00 morgen (18.20ct)
✓ Ladeplan gespeichert: 45 Stunden, 2 Ladungen (1 morgen)
📊 Statistik:
- Planungsfenster: 45 Stunden
- Tomorrow-Daten: ✓ Ja
- Ladungen heute: 1
- Ladungen morgen: 1
- Energie heute: 5.0 kWh @ 17.80 ct/kWh
- Energie morgen: 0.5 kWh @ 18.20 ct/kWh
=== Optimierung abgeschlossen ===
```
**After `pyscript.execute_charging_schedule` (during charging hour)**:
```
Suche Ladeplan für 2025-11-20 02:00 Uhr (lokal)
✓ Gefunden: 2025-11-20T02:00:00+01:00
⚡ Stunde 02:00 [heute]: action=charge, power=-5000W, price=17.80ct
Grund: Rang 1/45: 17.80ct [heute]
🔋 AKTIVIERE LADEN mit 5000W
✓ Manuelles Laden aktiviert
```
**After `pyscript.execute_charging_schedule` (during auto hour)**:
```
Suche Ladeplan für 2025-11-20 15:00 Uhr (lokal)
✓ Gefunden: 2025-11-20T15:00:00+01:00
⚡ Stunde 15:00 [heute]: action=auto, power=0W, price=28.50ct
Grund: Rang 25 (nicht unter Top 2)
✓ Auto-Modus bereits aktiv
```
---
## Final Checklist Before Requesting Help
If you've tried everything above and still have issues, gather this info:
1. ✅ Home Assistant version:
- Settings → System → Info
2. ✅ PyScript version:
- Settings → Devices & Services → PyScript
3. ✅ Python version in HA:
```bash
docker exec homeassistant python --version
```
4. ✅ Complete error log:
- Settings → System → Logs
- Filter for "pyscript"
- Copy last 50 lines
5. ✅ Entity status:
- Check if these exist: `sensor.hastrom_flex_pro_ext`, `pyscript.battery_charging_schedule`
6. ✅ Service availability:
- List all `pyscript.*` services
7. ✅ File locations confirmed:
```bash
ls -la /config/pyscript/*.py
```
8. ✅ Recent manual test results:
- What happened when you called each service manually?
---
## Quick Reference Commands
```yaml
# Reload PyScript
service: pyscript.reload
# Test price fetch
service: pyscript.getprices_extended
# Test optimizer
service: pyscript.calculate_charging_schedule
# Test executor
service: pyscript.execute_charging_schedule
# Enable optimizer
service: input_boolean.turn_on
data:
entity_id: input_boolean.battery_optimizer_enabled
# Disable optimizer
service: input_boolean.turn_off
data:
entity_id: input_boolean.battery_optimizer_enabled
# Check schedule state
# Developer Tools → States → pyscript.battery_charging_schedule
# Check price sensor
# Developer Tools → States → sensor.hastrom_flex_pro_ext
```
---
## Contact & Support
If issues persist after following this guide:
1. Export logs: Settings → System → Advanced → Download Logs
2. Check PyScript GitHub issues: https://github.com/custom-components/pyscript
3. Home Assistant Community: https://community.home-assistant.io/
Include in your report:
- HA version
- PyScript version
- Complete error logs
- Output of validation script (`python3 validate_pyscript.py`)
- Steps already tried from this guide