Http SUBSCRIBE / NOTIFY (Session Initiation Protocol) - how?

I would like to implement a listener to an UPNP service. For that I need to subscribe (simple http request with some specific headers items - see code) and create an http instance for incoming notification.

Is there anything available in Node-RED what I can reuse?
I could not find "SUBSCRIBE" - only POST, GET, ... in the http nodes.
Any node.on for this kind of subscription, port 4000

> async function (baseUrl, path) {
>     const response = await request({
>       method: 'SUBSCRIBE',
>       baseURL: baseUrl,
>       url: path,
>       headers: {
>         CALLBACK: '<http://192.168.178.49:4000/sonos/events>',
>         NT: 'upnp:event',
>         TIMEOUT: 'Second-1800'
>       },
>       resolveWithFullResponse: true
>     })

You can have whatever method you desire.

HTTP Request node...
image

1 Like

some while ago I created a upnp node https://github.com/cinhcet/node-red-contrib-upnp
Lately I fixed some bugs which have not been published yet, but the basic functionality should work.

Looks interesting.
Is there any documentation for "receive event"?

UUID might be RINCON_5CAAFD00223601400 but also RINCON_5CAAFD00223601400_MR. Both show green.
Service type is what? I tried upnp:event but an error occurs.
Where do I have to enter the service endpoint -for instance "MediaRenderer/RenderingControl/Event"

Service type depends on what you want to receive events from.
I read sonos in your first post, so I guess you maybe want urn:schemas-upnp-org:service:AVTransport:1

You can also pull in the mediaRenderer node, which receives events from urn:schemas-upnp-org:service:AVTransport:1 and you can play, pause, stop, set media etc.

If you explain me what you want to do, I might can help. I went through the rabbit hole and have read a lot of the UPnP specifications.

About the UUID, you get it from discovery. Send the payload ssdp:all to the discovery node and it will shout out a lot of messages (put a debug node behind it). Then find the service you want to have and then also the associated UUID from that. But if it shows the green status, then it is already good :slight_smile: So you might already found the right one.

What error occurs?

I have just read in your post that you want to do rendering control,
then urn:schemas-upnp-org:service:RenderingControl:3 should be the service type.
However, rendering control is not really useful for a loudspeaker, except for changing the volume.

I would like to get notified about changes regarding playback state but also about volume changes.

The output from ssdp:all / node Discovery is for the relevant player:

USN: "uuid:RINCON_5CAAFD00223601400_MR::urn:schemas-upnp-org:service:AVTransport:1"
address: "192.168.178.37"
(more)

For node receive event, field Service Type:
urn:schemas-upnp-org:service:AVTransport:1
and in the configuration node, field uuid
RINCON_5CAAFD00223601400_MR

The node status turns green and the debug node provide the error:
Error: Service urn:schemas-upnp-org:service:AVTransport:1 not available

playback state is something you get from AVTransport, volume from renderingControl.

Can you post the complete output from the discovery for the relevant player? I might already have an idea why it might not work

can you maybe also post the device description xml file? During discovery, you should find the device description url somewhere in the message (headers.LOCATION), open that in the browser and post the content here.

UPnP is a complex topic, the little code you have shown above would definitively not do the right thing (or I misinterpret it), because the CALLBACK should not be the device you want to receive the state from, but an http endpoint the device will report its state to. Furthermore, you have to resubscribe after the timeout etc.

I googled myself for the device description xml of a sonos device (could be that it is a different one to yours) and it appears that sonos devices make use of so-called embedded upnp devices (just another unnecessary feature of the upnp spec)
I have not implement this, since I don't own a device that has this feature.

If you are willing to test things, I can try to implement this, which should be pretty easy, however, it is hard to do for me since I cannot test it.

1 Like

Testing: Yes - sure I will do the tests. One restriction: from 16 to 25 of June I am not at home and don't have access to the SONOS devices.

Little Code: Yes, I know. The "little" code only does the "subscribe" but we need an event receiver, unsubscribe, renew subscription, ... - that's why your package is needed.

Additional info: There are 4 player endpoints I would like to subscribe to:
MediaRenderer/AVTransport/Event, MediaRenderer/RenderingControl/Event, MediaRenderer/GroupRenderingControl/Event, MediaRenderer/Queue/Event

and 2 global endpoints but so far I dont need them:
AlarmClock/Event, ZoneGroupTopology/Event

Before being able to subscribe, the event receiver must be up an running - otherwise the subscription will return error 412.

There are already packages providing the events node sonos and notify but they crash to often on my system.

Here is the requested output:
event - output.txt (14.2 KB)

Thanks for your help.

I just pushed a new version to github https://github.com/cinhcet/node-red-contrib-upnp
Best is to uninstall the old one first, since it depends on a package I updated which is installed from git as well (https://github.com/cinhcet/node-upnp-control-point this is the actual control point) and I don't know if npm is smart enough to update dependencies from github as well.

This is now untested code, since I don't own a device with embedded devices.

Let me know what you got. If it doesn't work, then you need to add some debugging output, I will tell you how.

The content of http://192.168.178.37:1400/xml/device_description.xml would also be great

you are lightning fast :slight_smile:

This XML file does not appear to have any style information associated with it. The document tree is shown below.
<root xmlns="urn:schemas-upnp-org:device-1-0">
<specVersion>
<major>1</major>
<minor>0</minor>
</specVersion>
<device>
<deviceType>urn:schemas-upnp-org:device:ZonePlayer:1</deviceType>
<friendlyName>192.168.178.37 - Sonos Play:5</friendlyName>
<manufacturer>Sonos, Inc.</manufacturer>
<manufacturerURL>http://www.sonos.com</manufacturerURL>
<modelNumber>S6</modelNumber>
<modelDescription>Sonos Play:5</modelDescription>
<modelName>Sonos Play:5</modelName>
<modelURL>http://www.sonos.com/products/zoneplayers/S6</modelURL>
<softwareVersion>58.1-77280</softwareVersion>
<swGen>2</swGen>
<hardwareVersion>1.13.1.7-2.1</hardwareVersion>
<serialNum>5C-AA-FD-00-22-36:1</serialNum>
<MACAddress>5C:AA:FD:00:22:36</MACAddress>
<UDN>uuid:RINCON_5CAAFD00223601400</UDN>
<iconList>
<icon>
<id>0</id>
<mimetype>image/png</mimetype>
<width>48</width>
<height>48</height>
<depth>24</depth>
<url>/img/icon-S6.png</url>
</icon>
</iconList>
<minCompatibleVersion>58.0-00000</minCompatibleVersion>
<legacyCompatibleVersion>58.0-00000</legacyCompatibleVersion>
<apiVersion>1.19.5</apiVersion>
<minApiVersion>1.1.0</minApiVersion>
<displayVersion>12.0</displayVersion>
<extraVersion/>
<roomName>Küche</roomName>
<displayName>Play:5</displayName>
<zoneType>12</zoneType>
<feature1>0x00000002</feature1>
<feature2>0x00018332</feature2>
<feature3>0x0001102e</feature3>
<seriesid>C100</seriesid>
<variant>1</variant>
<internalSpeakerSize>7</internalSpeakerSize>
<bassExtension>40.000</bassExtension>
<satGainOffset>0.000</satGainOffset>
<memory>256</memory>
<flash>256</flash>
#DEACTIVATION_STATE_TAG_AND_VALUE# #DEACTIVATION_TTL_TAG_AND_VALUE# #DEACTIVATION_DATE_TIME_TAG_AND_VALUE#
<flashRepartitioned>0</flashRepartitioned>
<ampOnTime>50</ampOnTime>
<retailMode>0</retailMode>
<serviceList>
<service>
<serviceType>urn:schemas-upnp-org:service:AlarmClock:1</serviceType>
<serviceId>urn:upnp-org:serviceId:AlarmClock</serviceId>
<controlURL>/AlarmClock/Control</controlURL>
<eventSubURL>/AlarmClock/Event</eventSubURL>
<SCPDURL>/xml/AlarmClock1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:MusicServices:1</serviceType>
<serviceId>urn:upnp-org:serviceId:MusicServices</serviceId>
<controlURL>/MusicServices/Control</controlURL>
<eventSubURL>/MusicServices/Event</eventSubURL>
<SCPDURL>/xml/MusicServices1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:AudioIn:1</serviceType>
<serviceId>urn:upnp-org:serviceId:AudioIn</serviceId>
<controlURL>/AudioIn/Control</controlURL>
<eventSubURL>/AudioIn/Event</eventSubURL>
<SCPDURL>/xml/AudioIn1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:DeviceProperties:1</serviceType>
<serviceId>urn:upnp-org:serviceId:DeviceProperties</serviceId>
<controlURL>/DeviceProperties/Control</controlURL>
<eventSubURL>/DeviceProperties/Event</eventSubURL>
<SCPDURL>/xml/DeviceProperties1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:SystemProperties:1</serviceType>
<serviceId>urn:upnp-org:serviceId:SystemProperties</serviceId>
<controlURL>/SystemProperties/Control</controlURL>
<eventSubURL>/SystemProperties/Event</eventSubURL>
<SCPDURL>/xml/SystemProperties1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:ZoneGroupTopology:1</serviceType>
<serviceId>urn:upnp-org:serviceId:ZoneGroupTopology</serviceId>
<controlURL>/ZoneGroupTopology/Control</controlURL>
<eventSubURL>/ZoneGroupTopology/Event</eventSubURL>
<SCPDURL>/xml/ZoneGroupTopology1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:GroupManagement:1</serviceType>
<serviceId>urn:upnp-org:serviceId:GroupManagement</serviceId>
<controlURL>/GroupManagement/Control</controlURL>
<eventSubURL>/GroupManagement/Event</eventSubURL>
<SCPDURL>/xml/GroupManagement1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-tencent-com:service:QPlay:1</serviceType>
<serviceId>urn:tencent-com:serviceId:QPlay</serviceId>
<controlURL>/QPlay/Control</controlURL>
<eventSubURL>/QPlay/Event</eventSubURL>
<SCPDURL>/xml/QPlay1.xml</SCPDURL>
</service>
</serviceList>
<deviceList>
<device>
<deviceType>urn:schemas-upnp-org:device:MediaServer:1</deviceType>
<friendlyName>192.168.178.37 - Sonos Play:5 Media Server</friendlyName>
<manufacturer>Sonos, Inc.</manufacturer>
<manufacturerURL>http://www.sonos.com</manufacturerURL>
<modelNumber>S6</modelNumber>
<modelDescription>Sonos Play:5 Media Server</modelDescription>
<modelName>Sonos Play:5</modelName>
<modelURL>http://www.sonos.com/products/zoneplayers/S6</modelURL>
<UDN>uuid:RINCON_5CAAFD00223601400_MS</UDN>
<serviceList>
<service>
<serviceType>urn:schemas-upnp-org:service:ContentDirectory:1</serviceType>
<serviceId>urn:upnp-org:serviceId:ContentDirectory</serviceId>
<controlURL>/MediaServer/ContentDirectory/Control</controlURL>
<eventSubURL>/MediaServer/ContentDirectory/Event</eventSubURL>
<SCPDURL>/xml/ContentDirectory1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:ConnectionManager:1</serviceType>
<serviceId>urn:upnp-org:serviceId:ConnectionManager</serviceId>
<controlURL>/MediaServer/ConnectionManager/Control</controlURL>
<eventSubURL>/MediaServer/ConnectionManager/Event</eventSubURL>
<SCPDURL>/xml/ConnectionManager1.xml</SCPDURL>
</service>
</serviceList>
</device>
<device>
<deviceType>urn:schemas-upnp-org:device:MediaRenderer:1</deviceType>
<friendlyName>Küche - Sonos Play:5 Media Renderer</friendlyName>
<manufacturer>Sonos, Inc.</manufacturer>
<manufacturerURL>http://www.sonos.com</manufacturerURL>
<modelNumber>S6</modelNumber>
<modelDescription>Sonos Play:5 Media Renderer</modelDescription>
<modelName>Sonos Play:5</modelName>
<modelURL>http://www.sonos.com/products/zoneplayers/S6</modelURL>
<UDN>uuid:RINCON_5CAAFD00223601400_MR</UDN>
<serviceList>
<service>
<serviceType>urn:schemas-upnp-org:service:RenderingControl:1</serviceType>
<serviceId>urn:upnp-org:serviceId:RenderingControl</serviceId>
<controlURL>/MediaRenderer/RenderingControl/Control</controlURL>
<eventSubURL>/MediaRenderer/RenderingControl/Event</eventSubURL>
<SCPDURL>/xml/RenderingControl1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:ConnectionManager:1</serviceType>
<serviceId>urn:upnp-org:serviceId:ConnectionManager</serviceId>
<controlURL>/MediaRenderer/ConnectionManager/Control</controlURL>
<eventSubURL>/MediaRenderer/ConnectionManager/Event</eventSubURL>
<SCPDURL>/xml/ConnectionManager1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:AVTransport:1</serviceType>
<serviceId>urn:upnp-org:serviceId:AVTransport</serviceId>
<controlURL>/MediaRenderer/AVTransport/Control</controlURL>
<eventSubURL>/MediaRenderer/AVTransport/Event</eventSubURL>
<SCPDURL>/xml/AVTransport1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-sonos-com:service:Queue:1</serviceType>
<serviceId>urn:sonos-com:serviceId:Queue</serviceId>
<controlURL>/MediaRenderer/Queue/Control</controlURL>
<eventSubURL>/MediaRenderer/Queue/Event</eventSubURL>
<SCPDURL>/xml/Queue1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:GroupRenderingControl:1</serviceType>
<serviceId>urn:upnp-org:serviceId:GroupRenderingControl</serviceId>
<controlURL>/MediaRenderer/GroupRenderingControl/Control</controlURL>
<eventSubURL>/MediaRenderer/GroupRenderingControl/Event</eventSubURL>
<SCPDURL>/xml/GroupRenderingControl1.xml</SCPDURL>
</service>
<service>
<serviceType>urn:schemas-upnp-org:service:VirtualLineIn:1</serviceType>
<serviceId>urn:upnp-org:serviceId:VirtualLineIn</serviceId>
<controlURL>/MediaRenderer/VirtualLineIn/Control</controlURL>
<eventSubURL>/MediaRenderer/VirtualLineIn/Event</eventSubURL>
<SCPDURL>/xml/VirtualLineIn1.xml</SCPDURL>
</service>
</serviceList>
<X_Rhapsody-Extension xmlns="http://www.real.com/rhapsody/xmlns/upnp-1-0">
<deviceID>urn:rhapsody-real-com:device-id-1-0:sonos_1:RINCON_5CAAFD00223601400</deviceID>
<deviceCapabilities>
<interactionPattern type="real-rhapsody-upnp-1-0"/>
</deviceCapabilities>
</X_Rhapsody-Extension>
<qq:X_QPlay_SoftwareCapability xmlns:qq="http://www.tencent.com">QPlay:2</qq:X_QPlay_SoftwareCapability>
<iconList>
<icon>
<mimetype>image/png</mimetype>
<width>48</width>
<height>48</height>
<depth>24</depth>
<url>/img/icon-S6.png</url>
</icon>
</iconList>
</device>
</deviceList>
</device>
</root>

What input is required in the config node?

With that data I get a red status: Device RIN... lost.

What is service type in event node? upnp:event does not work

In the event node urn:schemas-upnp-org:service:AVTransport:1 as I said before.
And don't use "use hardcoded device description URL" and don't put something into "device description url" and especially not an event URL.
The option "use hardcoded device description URL" is for avoiding discovery, which in some networks is unreliable.

Edit: If you want to use the hardcoded description URL, you have to put http://192.168.178.37:1400/xml/device_description.xml into it, but this would assume that the device always has the same IP. If you use discovery, it can deal with changing IPs etc.

amazing - well done! :grinning: :clap:
Discovery works and a lot of events come in.
I will now make a list, what I do receive and what is missing.

When I use hardcoded (with static ip address) the discovery is omitted what means faster and more reliable?

great :slight_smile:

If you also want rendering control, you need a second event node with urn:schemas-upnp-org:service:RenderingControl:1 as the service type.

Yes, the discovery sometimes makes problems, so if you go with the hardcoded device description url and a static IP, it is more reliable and also a tiny bit faster.

One disclaimer though: UPnP is really a complex topic, mainly because I think there is not a single implementation out there that adheres to the spec (libupnp for linux does not completely, and my one also not). Therefore, I do not promise that it does not crash, ok?
That is also the reason why I never published that node on npm (also due to lack of documentation).
Still, for my UPnP devices, that node runs stable for over a year without any problems and is used every day.

Report any problems and I can see what I can do.

1 Like

@Steve-Mcl: Thanks - that's a good trick. It works fine and I receive the subscription id from the server.

Do you have a similar "trick" for the http-in node. I need a "NOTIFY" method as the server expects a http response with confirmation 200 OK.