Ваши комментарии

Not sure this is an appropiate response here, but I have stopped using the Iridium Sonos driver due to been on the Sonos beta and this driver essentially never working for me.


On my Iridium server i am running an opensource Node application called Node-Sonsos-Http-API (https://github.com/jishi/node-sonos-http-api/) and on my Iridium server i have created a basic module, which leverages the application to do all the UPNP work. So far this has been running solid for 8 months, and I am currently running Sonos 8.0.371245110 


I have not converted all the functions to this model, but the following will show the basic framework I use, and is maintainable


Apologies if this is inappropriate here, and please delete if needed


Sonos_API = function(DriverName)
{
   //-------------------------------------------------------
   // Driver Data
   //------------------------------------------------------- 
   this.DriverName = DriverName;
   this.device;
   this.Online = false;
   var that;
   
   var deviceList = [];
   this.error = false; // Error flag
  
   // Log Levels
   // 0 = No logging 
   // 1 = Information
   // 2 = Verbose
   // 3 = Debug
   var loggingLevel = 3;
   //-------------------------------------------------------
   // Device Initialization
   //------------------------------------------------------- 
   function initialization() // Initialization method of the class instance
   {
 
      //this.device= IR.CreateDevice(IR.DEVICE_CUSTOM_HTTP_TCP, this.DriverName, {Host: "172.16.1.5", Port: 5005, ReceiveWaitTimeMax: 5000}); // Defining the indicator of the base driver by its name 
      this.device= IR.GetDevice(this.DriverName); // Defining the indicator of the base driver by its name 
      that = this; // Receiving the link to the object for its using inside the function
      //-------------------------------------------------------
      // Device Online
      //-------------------------------------------------------     
      IR.AddListener(IR.EVENT_START,that.device,function()
      {
         Log("DEVICE is Initializing..."); // Write to the log that the device is Online
         
         Log("DEVICE is Initialized"); // Write to the log that the device is Online
      }, that);
        
      //-------------------------------------------------------
      // Device Online
      //-------------------------------------------------------     
      IR.AddListener(IR.EVENT_ONLINE, that.device, function(text)
      { 
         Log("DEVICE is Online"); // Write to the log that the device is Online
         that.Online = true; // Assign the true value to the that.Online variable
         deviceList = getSonosDevices();
      }, that);
      //-------------------------------------------------------
      // Device Offline
      //-------------------------------------------------------
      IR.AddListener(IR.EVENT_OFFLINE, that.device, function(text)
      { 
         Log("DEVICE is Offline"); // Write to the log that the device is Offline
         that.Online = false; // Assign the false value to the that.Online variable
      }, that);  
      //-------------------------------------------------------
      // Receive Text
      //-------------------------------------------------------
      IR.AddListener(IR.EVENT_RECEIVE_TEXT, that.device, function(text)
      {
         Log("Text Received: " + text);  // Output the received data in the log
      }, that);
        
      //-------------------------------------------------------
      // Channel Set
      //-------------------------------------------------------
      IR.AddListener(IR.EVENT_CHANNEL_SET, that.device, function(name, value) {
         name  = TrimString(name);
         value = TrimString(value);
        
         Log("Issue Command: " + name + " :: " + value, "Verbose");
        
         //name is the command
         switch (name){
            case "Speak":
                //a1 = arm away
                var payload = value.split(":");
                
                var zone = payload[0] ? payload[0].toString() : 'Kitchen';
                var announcement = (payload[1]) ? payload[1].toString() : 'Just Because I Can!';
                               
                announce(zone, announcement)
                break;
         }
      }, that);
  
   }
   
   function getSonosDevices ()
   {
      var sonosDevices = [];
      NodeSonosAPIrequest = function(in_callback)
      {
         that.device.SetParameters({ConnectWaitTimeMax: 5000, ReceiveWaitTimeMax: 10000});
         that.device.Connect();
         that.device.SendEx(
         {
            Type: "GET",
            Url: "/zones",
            cbReceiveText: function(text, code, headers) 
            {
               if (code != 200) return; //parse other error codes
               var resp = JSON.Parse(text);
               //IR.Log(text); 
               that.device.Disconnect();                    
               in_callback(resp);
            },
         });
      };
      //Attach data to channels here
      NodeSonosAPIrequest(function(resp)
      {
         for (var i = 0; i < resp.length; i++) {
            IR.Log(resp[i].coordinator.roomName);
            sonosDevices[i] = resp[i].coordinator.roomName;
         }
         //IR.GetDevice("mqtt").Set("temp",coordinators.roomName); 
         //IR.GetDevice("mqtt").Set("pressure",resp.main.pressure);
      });
      return sonosDevices;
   }
   function announce(Zone, Message, Volume) 
   {
      var vol = (Volume) ? Volume.toString() : '40';
      var httpCmd = 'Get,/' + Zone + '/say/' + encodeURIComponent(Message) + '/' + encodeURIComponent(vol);
      Log("Speaking ["+ Message +"]");
      Log("Sending: " + httpCmd, "Debug");  // Output the received data in the log
      that.device.Send([httpCmd]);
   }
   
   
   
   //**************************************************\\
   var TrimString = function (str) {
      var localStr = str;
      if (!str) return str; // Don't alter the empty string
      try {
         return str.replace(/^\s+|\s+$/g, ""); // Regular expression magic, barfs if the type is a number,
                                                // but we need to be able to trim Strings that are made up of numbers, eg " 0" -> "0"
      }
      
      catch(err) {
         return localStr;
      }
   }
   
   var Log = function(logText, logMode) {
      var log = logMode ? logMode.toString() : 'Info';
      switch(log) {
         case 'Verbose':
            if (loggingLevel >= 2)  IR.Log("VERBOSE: [" + that.DriverName + "] " + logText);
            break;
            
         case 'Debug':
            if (loggingLevel >= 3)  IR.Log("  DEBUG: [" + that.DriverName + "] " + logText);
            break;
                
         case 'Error':
            if (loggingLevel >= 1)  IR.Log("  ERROR: [" + that.DriverName + "] " + logText);
            break;
          
         default:
            if (loggingLevel >= 1)  IR.Log("   INFO: [" + that.DriverName + "] " + logText);
            break;
      }
   }
  
   //-------------------------------------------------------
   // Public
   //-------------------------------------------------------
   this.Init = initialization; // Make the initialization function public
   this.Speak = announce;
};  
var SonosAPI = new Sonos_API("Node-Sonos");
SonosAPI.Init();
var primaryAnnouncementZone = "Kitchen";
SonosAPI.Speak(primaryAnnouncementZone,"System Update, The Iridium Pro Server has been restarted.","50");


From there to get a list of Favorites i would just send a request of the following to the Node Sonos Instance


http://nodeSonosAPI/favourites


and then from the list returned, i can play it in the zone with the following command


http://nodeSonosAPI/zone/favourite/item name


This is what the code might look like, as an example of how easy this can be to work with Iridium and Sonos


   // Helper Function to Play a playlist in group or zone, with an optional volume
   function playPlaylist(Zone, Playlist, Volume) {
      playQueue(Zone, Playlist, "Playlist", Volume);
   }    // Helper Function to Play a favorite in group or zone, with an optional volume
   function playFavorite(Zone, Favorite, Volume) 
   {
      playQueue(Zone, Favorite, "Favorite", Volume);
   }    // Worker Function to Play a favorite or playlist in group or zone, with an optional volume
   function playQueue(Zone, QueueName, QueueType, Volume) {
      var queue = '';
      if (QueueType == "Playlist") { queue = "playlist"; }
      else if (QueueType == "Favorite") { queue = "favorite"; }
      else { break; }       
      var httpCmd = 'Get,/' + Zone + '/' + encodeURIComponent(queue) + '/' + encodeURIComponent(QueueName);
      Log("Playing "+ QueueType + ' ' + QueueName +" in " + Zone);
      Log("Sending: " + httpCmd, "Debug");  // Output the received data in the log
      that.device.Send([httpCmd]);       if (Volume) {
         // If the Volume is also provided, we will update Sonos to implement this request also
         var httpCmd = 'Get,/' + Zone + '/volume/' + encodeURIComponent(volume);
         Log("Setting Volume to "+ Volume + " in " + Zone);
         Log("Sending: " + httpCmd, "Debug");  // Output the received data in the log
         that.device.Send([httpCmd]);
      } else {
         Log("No Change to Volume to "+ Volume + " in " + Zone);
      }
   }
   


Both reply with JSON, so parsing is not hard in Iridium.

Done ! :)




Сервис поддержки клиентов работает на платформе UserEcho