diff --git a/internal/onvif/init.go b/internal/onvif/init.go
index 014c5e18..b8b4fca6 100644
--- a/internal/onvif/init.go
+++ b/internal/onvif/init.go
@@ -70,6 +70,10 @@ func onvifDeviceService(w http.ResponseWriter, r *http.Request) {
// important for Hass: Media section
res = onvif.GetCapabilitiesResponse(r.Host)
+ case onvif.ActionGetServices:
+ // important for Unifi: Media section
+ res = onvif.GetServicesResponse(r.Host)
+
case onvif.ActionGetSystemDateAndTime:
// important for Hass
res = onvif.GetSystemDateAndTimeResponse()
@@ -95,8 +99,13 @@ func onvifDeviceService(w http.ResponseWriter, r *http.Request) {
case onvif.ActionGetProfiles:
// important for Hass: H264 codec, width, height
+ // important for Unifi: framerate, bitrate, quality
res = onvif.GetProfilesResponse(streams.GetAll())
+ case onvif.ActionGetVideoSources:
+ // important for Unifi: framerate, resolution
+ res = onvif.GetVideoSourcesResponse(streams.GetAll())
+
case onvif.ActionGetStreamUri:
host, _, err := net.SplitHostPort(r.Host)
if err != nil {
@@ -107,6 +116,10 @@ func onvifDeviceService(w http.ResponseWriter, r *http.Request) {
uri := "rtsp://" + host + ":" + rtsp.Port + "/" + onvif.FindTagValue(b, "ProfileToken")
res = onvif.GetStreamUriResponse(uri)
+ case onvif.ActionGetSnapshotUri:
+ uri := "http://" + r.Host + "/api/frame.jpeg?src=" + onvif.FindTagValue(b, "ProfileToken")
+ res = onvif.GetSnapshotUriResponse(uri)
+
default:
http.Error(w, "unsupported action", http.StatusBadRequest)
log.Debug().Msgf("[onvif] unsupported request:\n%s", b)
diff --git a/pkg/onvif/server.go b/pkg/onvif/server.go
index f8f2883c..df53dfab 100644
--- a/pkg/onvif/server.go
+++ b/pkg/onvif/server.go
@@ -16,6 +16,7 @@ const (
ActionGetServiceCapabilities = "GetServiceCapabilities"
ActionGetProfiles = "GetProfiles"
ActionGetStreamUri = "GetStreamUri"
+ ActionGetSnapshotUri = "GetSnapshotUri"
ActionSystemReboot = "SystemReboot"
ActionGetServices = "GetServices"
@@ -65,6 +66,32 @@ func GetCapabilitiesResponse(host string) string {
`
}
+func GetServicesResponse(host string) string {
+ return `
+
+
+
+
+ http://www.onvif.org/ver10/device/wsdl
+ http://` + host + `/onvif/device_service
+
+ 2
+ 5
+
+
+
+ http://www.onvif.org/ver10/media/wsdl
+ http://` + host + `/onvif/media_service
+
+ 2
+ 5
+
+
+
+
+`
+}
+
func GetSystemDateAndTimeResponse() string {
loc := time.Now()
utc := loc.UTC()
@@ -142,7 +169,7 @@ func GetServiceCapabilitiesResponse() string {
-
+
@@ -171,14 +198,27 @@ func GetProfilesResponse(names []string) string {
for i, name := range names {
buf.WriteString(`
- ` + name + `
-
- H264
-
- 1920
- 1080
-
-
+ ` + name + `
+
+ ` + name + `
+ H264
+
+ 1920
+ 1080
+
+
+ 29.97003
+ 1
+ 5000
+
+ 4
+ PT1000S
+
+
+ ` + name + `
+ ` + strconv.Itoa(i) + `
+
+
`)
}
@@ -190,15 +230,55 @@ func GetProfilesResponse(names []string) string {
return buf.String()
}
+
+func GetVideoSourcesResponse(names []string) string {
+ buf := bytes.NewBuffer(nil)
+ buf.WriteString(`
+
+
+ `)
+
+ for i, _ := range names {
+ buf.WriteString(`
+
+ 29.97003
+
+ 1920
+ 1080
+
+ `)
+ }
+
+ buf.WriteString(`
+
+
+`)
+
+ return buf.String()
+}
+
func GetStreamUriResponse(uri string) string {
return `
- ` + uri + `
+ ` + uri + `
`
}
+
+func GetSnapshotUriResponse(uri string) string {
+ return `
+
+
+
+
+ ` + uri + `
+
+
+
+`
+}