mirror of
https://github.com/kerberos-io/onvif.git
synced 2026-08-23 15:08:33 +00:00
Two gaps in the previous commit's guard. Strict inequality was not enough. A client timeout one millisecond above PullTimeout passed, and the test pinned that as valid — but the client ceiling also has to cover dial, TLS and the response transfer on top of the poll it outlasts, which on a cellular bearer is hundreds of milliseconds. Require minClientHeadroom (5s) above PullTimeout. The error was a bare fmt.Errorf, so callers could not tell it from the transient pull/renew/recreate failures they retry. A consumer that retries this one loops forever on a configuration that can never succeed. ErrInvalidOptions is a sentinel they can short-circuit on. Zero stays accepted: it is the SDK's default when a caller passes no client, so rejecting it would break every default consumer. The comment no longer claims that is safe — the caller interface documents that ctx cannot interrupt an in-flight SOAP call, so an unbounded client is the one case nothing can unwedge.
30 lines
1.2 KiB
Go
30 lines
1.2 KiB
Go
// Package stream is a typed, channel-based consumer for ONVIF device
|
|
// events. It hides the SOAP/XML, pull-point subscription lifecycle,
|
|
// subscription renewal and vendor-specific topic conventions behind a
|
|
// single Event stream.
|
|
//
|
|
// # Usage
|
|
//
|
|
// dev, _ := onvif.NewDevice(onvif.DeviceParams{Xaddr: "...", Username: "...", Password: "..."})
|
|
// s, err := stream.NewStream(ctx, dev, stream.Options{DeviceID: "front-door"})
|
|
// if err != nil { /* construction failed: auth, network, or no event support */ }
|
|
// defer s.Close()
|
|
//
|
|
// for ev := range s.Events() {
|
|
// switch ev.Kind {
|
|
// case stream.KindMotion:
|
|
// if ev.State == stream.StateActive { /* start recording */ }
|
|
// }
|
|
// }
|
|
//
|
|
// NewStream performs network I/O so auth and reachability failures
|
|
// surface synchronously, and rejects a client timeout that cannot
|
|
// outlast PullTimeout with ErrInvalidOptions. Events and Errors close when the Stream stops;
|
|
// Errors sends are non-blocking so a stalled consumer drops older
|
|
// errors rather than blocking the pull loop. After a silent reconnect,
|
|
// the next batch's events carry Event.AfterReconnect=true.
|
|
//
|
|
// See topics.go for the verified topic→Kind mapping across AXIS,
|
|
// Hikvision, Avigilon, Hanwha, Bosch and Dahua.
|
|
package stream
|