This document explains how to run Whistleblower's test suite and add tests for new BAS sites.
# Validate all site configs (syntax, structure, patterns)
python tests/test_configs.py
# Run functional tests on reachable sites
python tests/test_functional.pyWhistleblower includes two automated test scripts:
Validates the syntax and structure of all site configuration files without requiring network access.
What it checks:
- ✅ JSON syntax (valid parsing)
- ✅ Required fields (name, base_url, login, watch)
- ✅ Login configuration (user_selector, pass_selector, submit_selector, success_selector)
- ✅ Selector validity (non-empty strings)
- ✅ Watch targets (each has name and url)
- 🔷 Login pattern detection (Niagara vs. Meatball vs. Custom)
Usage:
python tests/test_configs.pyExample output:
============================================================
WHISTLEBLOWER SITE CONFIG TEST SUITE
============================================================
Found 5 config files to test
============================================================
Testing: localNiagara.json
============================================================
✅ JSON syntax valid
✅ Required fields present
✅ Login config valid
✅ Selectors look valid
✅ Watch targets: 3
✓ Target 0: prelogin
✓ Target 1: login
✓ Target 2: dashboard
🔷 Detected: Niagara-style login (multi-step capable)
✅ CONFIG VALID: localNiagara.json
[... more configs ...]
============================================================
SUMMARY: 5/5 configs valid
Runs whistleblower.py against each site config and verifies execution completes without fatal errors. Gracefully handles unreachable systems (network, credentials).
What it tests:
- Whistleblower.py execution with config
- Process exit codes
- Error detection in stdout/stderr
- Timeout handling (per-config timeouts)
Usage:
python tests/test_functional.pyExample output:
============================================================
WHISTLEBLOWER FUNCTIONAL COMPATIBILITY TESTS
============================================================
Niagara multi-step login - LOCAL SYSTEM
============================================================
FUNCTIONAL TEST: localNiagara
Running: whistleblower.py --config sites\localNiagara.json
Timeout: 90 seconds
(This will attempt to log in and capture targets)
------------------------------------------------------------
STDOUT:
[Playwright browser launch...]
✅ Execution successful (exit code 0)
============================================================
Meatball Tracers - SKIP if network unavailable
============================================================
FUNCTIONAL TEST: 196-21test
...
⚠️ Timeout after 30 seconds
This could mean:
- Network connectivity issue (host unreachable)
- System is responding slowly
- Login credentials incorrect
============================================================
FUNCTIONAL TEST SUMMARY
============================================================
✅ PASS localNiagara - Success
⚠️ SKIP 196-21test - Timeout - network expected
⚠️ SKIP 196-22test - Timeout - network expected
...
Create a new site configuration in sites/{name}.json:
{
"name": "my-new-building",
"base_url": "https://bms.example.com",
"ignore_https_errors": true,
"login": {
"username": "operator",
"password": "secret",
"user_selector": "#user_field",
"pass_selector": "#password_field",
"submit_selector": "button[type='submit']",
"success_selector": "main, [role='main']"
},
"watch": [
{
"name": "main_dashboard",
"url": "https://bms.example.com/dashboard",
"root_selector": "body",
"settle_ms": 5000
}
]
}See sites/README.md for template options and docs/TEMPLATES.md for detailed configuration guide.
python tests/test_configs.pyThe new config will be automatically discovered and tested. Check that:
- JSON is valid
- All required fields are present
- Login pattern is correctly detected
python tests/test_functional.pyIf your site is reachable:
- Whistleblower will attempt login
- Targets will be captured
- Artifacts appear in
data/{name}/TIMESTAMP/
If unreachable:
- Test gracefully times out (expected for remote/demo systems)
- No false failures
✅ JSON syntax valid
✅ Required fields present
✅ Login config valid
✅ Selectors look valid
✅ Watch targets: N
🔷 Detected: [Pattern]
✅ CONFIG VALID
Action: Ready to test functionally
| Issue | Fix |
|---|---|
❌ JSON parse error |
Fix JSON syntax (missing comma, quote, bracket) |
❌ Missing required fields |
Add name, base_url, login, or watch |
❌ Missing login fields |
Add user_selector, pass_selector, submit_selector |
❌ Invalid selectors |
Ensure selectors are non-empty strings (use browser DevTools to verify) |
❌ Target missing name or url |
Each watch target needs name and url fields |
| Status | Meaning | Action |
|---|---|---|
| ✅ PASS | System is reachable, login succeeded, capture completed | Verify artifacts in data/ |
| Network/credentials prevented capture (expected for remote) | Manual test if available |
# Ensure config is in sites/ directory
ls sites/ | grep -i your-site-name# Validate JSON syntax using PowerShell
Get-Content sites/your-config.json | ConvertFrom-Json- Use
bootstrap_recorder.pyto auto-discover selectors:python bootstrap_recorder.py
- Verify selectors in browser DevTools (F12)
- Test CSS selectors in browser console:
document.querySelector("#id")
- Increase timeout in
tests/test_functional.py(changetimeout_secparameter) - Check if system is running and accessible
- Verify credentials are correct
- Check network connectivity
When adding new BAS vendors:
-
Discover (first time only)
python bootstrap_recorder.py # Outputs: sites/new-vendor.bootstrap.json -
Validate
python tests/test_configs.py # Should show: ✅ CONFIG VALID
-
Test
python tests/test_functional.py # Check for: ✅ PASS or ⚠️ SKIP (expected)
-
Verify Artifacts
ls data/new-vendor/ | Sort-Object -Descending | Select-Object -First 1 # Latest timestamp contains your captures
-
Document (optional)
- Add to sites/README.md vendor table
- Update sites/templates-registry.json with profile
Current test suite validates:
- ✅ Configuration syntax (JSON parsing)
- ✅ Configuration structure (required fields)
- ✅ Whistleblower.py execution with configs
- ✅ Login pattern detection
- ✅ Multi-step login handling (Niagara)
- ✅ Single-step login handling (Meatball, React)
Not tested (manual):
- Screenshot quality/completeness
- DOM capture accuracy
- Selector accuracy on specific systems
- Timing issues (settle_ms tuning)
- Custom credential providers
To integrate tests into your CI/CD pipeline:
# Example GitHub Actions workflow
- name: Validate all site configs
run: python tests/test_configs.py
- name: Run functional tests
run: python tests/test_functional.py
# Only on self-hosted runners with network access to test systemsCheck README.md for troubleshooting and TEMPLATES.md for configuration details.