- Add HTTPProber: parallel HEAD+GET on ports 80/8080, extracts Server header
- Reduce mDNS timeout from 1s to 100ms using context wrapper around
mdns.Query (HomeKit devices respond in 2-10ms, no need to wait 1s)
- Add Trassir (F0:23:B9) and ZOSI (00:05:FE) to camera OUI database
- Probe response time improved from ~1s to ~110ms for reachable devices
Fast (~1-3s) endpoint that gathers network info about a device
before full stream discovery. Runs ping first, then parallel probes.
Features:
- Ping with ICMP + TCP fallback (works without root)
- Reverse DNS hostname lookup
- ARP table MAC address + OUI vendor identification (2403 entries, 51 camera vendors)
- mDNS HomeKit detection (camera/doorbell, paired status)
- Extensible Prober interface for adding new probe types
- 3-second overall timeout, parallel execution
Response includes "type" field:
- "unreachable" - device not responding
- "standard" - normal IP camera (RTSP/HTTP/ONVIF flow)
- "homekit" - Apple HomeKit camera (PIN pairing flow)
Add padding to overcome aiohttp 64KB buffer in HA Supervisor.
Problem:
- HA Supervisor uses aiohttp with 64KB StreamResponse buffer
- Small SSE events (~200-500 bytes) were buffered until connection closed
- Users saw all streams appear at once instead of real-time updates
Solution:
- Detect Ingress mode via X-Ingress-Path header
- Add 64KB SSE comment padding to fill proxy buffers
- Increase progress interval to 3 sec in Ingress mode (reduce traffic)
- Normal mode (Docker/direct) unchanged - works exactly as before
Traffic impact:
- Normal mode: ~17KB per scan (unchanged)
- Ingress mode: ~2-3MB per scan (acceptable for real-time updates)
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
Problem:
- WriteTimeout was 30 seconds
- Progress only sent when values changed
- Long ffprobe tests (7-8s each) could cause 30+ seconds without writes
- Result: "curl: (18) transfer closed with outstanding read data remaining"
Solution:
- Increase WriteTimeout from 30s to 5 minutes
- Send progress every 1 second (instead of 3 seconds)
- Always send progress, even if values unchanged
- Guarantees write every second, preventing timeout
Changes:
- internal/config/config.go: WriteTimeout 30s → 5min
- internal/camera/discovery/scanner.go:
- Progress ticker 3s → 1s
- Remove "only if changed" check
- Always send progress to keep connection alive
Testing:
- HiWatch camera with 591 streams: Previously timed out at ~338/591
- Should now complete all 591 streams without timeout
JavaScript fixes:
- Fix Invalid URL error in stream-discovery.js by adding window.location.origin as base URL
- Fix SSE race condition: ensure all stream_found events sent before complete event
- Comment unused eventType variable in stream-discovery.js
- Comment unused FrigateGenerator import in config-panel.js
- Fix quote style (double to single quotes)
Go fixes:
- Add sync.WaitGroup for result collector to prevent premature SSE closure
- Add logging for stream_found events
- Fix ERR_INCOMPLETE_CHUNKED_ENCODING by waiting for all streams to be sent
ESLint setup:
- Add ESLint v8.57.1 with .eslintrc.cjs config for ES2022 modules
- Add npm scripts for lint and lint:fix
- Update .gitignore for node_modules and package-lock.json
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Fix critical scanner.go bug: ineffective break in select (SA4011)
Use labeled break to properly exit loop on context cancellation
- Add error checking for all file.Close() and resp.Body.Close()
Prevent resource leaks in loader, onvif_simple, and tester
- Add error checking for fmt.Sscanf() calls in tester.go
Prevent silent parse failures for FPS and bitrate extraction
- Add error checking for all SSE streamWriter calls
Explicit ignore with _ = for SendJSON and SendError
- Remove unused sync.RWMutex field from SearchEngine
- Refactor if/else to switch for CodecType (staticcheck QF1003)
More idiomatic Go code in stream tester
All 20 linter issues resolved. Code compiles and runs correctly.
- Update module path from github.com/strix-project/strix to github.com/eduard256/Strix
- Update all Go imports to use new repository path
- Update documentation links in README.md and CHANGELOG.md
- Update GitHub URLs in .goreleaser.yaml
- Fix placeholder documentation URL in DATABASE_FORMAT.md
- Remove old log files
This commit addresses the issue where HTTP-based cameras (JPEG/MJPEG) were not being
discovered due to incomplete authentication variant generation.
Changes:
- Builder now generates 4 authentication variants for each HTTP/HTTPS URL:
1. No authentication (for open cameras)
2. Basic Auth only (embedded credentials in URL)
3. Query parameters only (user=X&pwd=Y)
4. Basic Auth + Query parameters (combined approach)
- Scanner updated to use BuildURLsFromEntry instead of BuildURL for popular patterns,
ensuring all authentication variants are tested
- Preserved existing query parameter values (e.g., channel=1 remains unchanged)
This fix enables discovery of cameras that require different authentication methods,
including those that only accept Basic Auth headers, query parameters, or combinations.
Tested with ZOSI ZG23213M camera - increased discovery from 0 to 9 working streams.
Major architectural improvement to eliminate duplicate credential embedding
and simplify authentication logic across the codebase.
Changes:
- Builder now generates all URL variants with proper authentication upfront
* RTSP: generates URLs with embedded credentials and without (for open cameras)
* HTTP/JPEG/MJPEG: generates variants with query params and for Basic Auth
- Tester simplified to only test ready-to-use URLs without modification
* Removed auth chain logic and multiple authentication method attempts
* Removed AuthMethod enum and related complexity
* Credentials automatically extracted from URLs when needed
- Scanner cleaned up by removing embedCredentialsInURL function
* All TestStream calls now use single URL parameter
* Removed AuthMethod from DiscoveredStream model
Benefits:
- Eliminates bug where credentials were added up to 3 times
- Centralizes all URL generation logic in one place (Builder)
- Cleaner, more maintainable code with clear separation of concerns
- Reduces complexity by ~200 lines of code
- All authentication scenarios still fully supported
Embed username:password@ credentials in discovered stream URLs for
basic_auth and combined authentication methods, making URLs directly
usable by clients without additional auth handling.
**Changes:**
- Add embedCredentialsInURL() function in scanner.go
- Embed credentials for basic_auth and combined methods only
- Skip embedding for no_auth, query_params, digest, url_embedded
- Handle edge cases: empty credentials, existing credentials in URL
- Apply in scanDirectStream() and testURLsConcurrently()
**Security:**
- URL encoding handled by url.UserPassword()
- Checks prevent credential duplication
- Only processes when username AND password are provided
**Results:**
Before: http://10.0.20.112/snapshot.jpg
After: http://admin:password@10.0.20.112/snapshot.jpg
Tested with Zosi ZG23213M camera - all 6 streams working correctly.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
- Fix ONVIF CallMethod response parsing (returns *http.Response, not structs)
- Add proper XML SOAP envelope parsing for GetProfiles and GetStreamUri
- Use correct types from xsd/onvif package (StreamType, TransportProtocol, ReferenceToken)
- Add strix binary to .gitignore
- Update configuration and API routes
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
This commit adds the complete Strix IP camera stream discovery system:
- Go-based API server with SSE support for real-time updates
- 3,600+ camera brand database with stream URL patterns
- Intelligent fuzzy search across camera models
- ONVIF discovery and stream validation
- RESTful API with health check, camera search, and stream discovery
- Makefile for building and deployment
- Comprehensive README documentation
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>