# Connecting your real Sungrow system Until you complete this, the app runs on synthetic mock usage data (`USE_MOCK_ISOLARCLOUD=true`, the default) so the rest of the app is fully usable in the meantime. ## What you need Two separate things, both free: 1. A **regular iSolarCloud account** -- the same one you use in the app to watch your system (username/password). 2. A **developer application** on the [Sungrow developer portal](https://developer-api.isolarcloud.com/), which gives you an **App Key** and **Secret Key** (and possibly an **RSA public key** -- see below). When creating the application, choose the **"V1 account login"** option rather than OAuth2.0 -- this app talks to the plain username/password login endpoint, not the OAuth2 authorization-code flow (which uses a different set of endpoints and an Application ID / redirect URI this app doesn't use). Approval is manual on Sungrow's side and can take a couple of days. ## Configure In `.env`: ``` USE_MOCK_ISOLARCLOUD=false ISOLARCLOUD_APP_KEY= ISOLARCLOUD_APP_SECRET= ISOLARCLOUD_USERNAME= ISOLARCLOUD_PASSWORD= ISOLARCLOUD_REGION=australia ``` If your application's portal page also shows an **RSA public key** (Settings -> Open API), some accounts require the password to be RSA-encrypted before it's sent rather than plain text. Paste it into `ISOLARCLOUD_RSA_PUBLIC_KEY` (see the commented example in `.env.example` for the multi-line quoting). If login fails with the key set, try leaving it blank -- not every app type needs it, and this app tries plain-text login as the alternative. Restart the app, then in Settings click **Test connection**. On success it lists every plant visible to your account -- pick the right one if you have more than one (most people don't, and can skip this). ## Verifying before trusting the numbers The exact wire format Sungrow expects was pieced together from a community-maintained, actively-used Home Assistant integration ([steven-g-w/HA-Sungrow](https://github.com/steven-g-w/HA-Sungrow)) built against this same portal and app type, since Sungrow's own docs are only visible after logging into the developer portal. Two things in `app/isolarcloud/client.py` are explicitly flagged there as best-effort rather than independently confirmed, and worth checking once you're connected: 1. **RSA password encryption**, if your app was issued a key -- the exact padding scheme isn't published anywhere public; `_encrypt_password` uses the common RSA/PKCS1v1.5 + base64 convention. If "Test connection" fails, check the portal's own "Documentation" page (visible after login) for the login endpoint's exact field/encryption spec, and adjust `_encrypt_password` if it differs. 2. **Which device is which.** iSolarCloud reports generation, load, and grid import/export per *device* (inverter, meter, ...), not per plant. `fetch_interval_data` assumes one meter device (for import/export/load) and one inverter device (for generation), which fits the common single-inverter household setup this app targets. Run: ```bash python scripts/verify_isolarcloud_cli.py devices --ps-id ``` and confirm it finds exactly one of each. If your system has multiple inverters or a different device layout, `fetch_interval_data` in `app/isolarcloud/client.py` will need adjusting to combine them. Then check the actual numbers look right: ```bash python scripts/verify_isolarcloud_cli.py history --hours 6 ``` Compare the printed generation/load/import/export figures against what the iSolarCloud app itself shows for the same window. Also worth noting at this point, since it affects how accurate the time-of-use plan comparisons can be: - **History retention**: how far back the minute-data endpoint actually returns data for your account (days? weeks? months?). The app is designed to be honest about small sample sizes and improve automatically as local history accumulates either way. - **True interval resolution**: confirm you're actually getting 5-minute granularity, not a coarser aggregate -- time-of-use plans need at least 30-minute resolution to be modeled accurately. Once satisfied, the scheduler will poll your real plant on the same schedule it was polling mock data -- no other change needed.