Error handling
SOAP uses Fault
elements to return errors for failed requests. Your music service should always return HTTP status code values of 500 Internal Server Error with any SOAP fault it throws regardless of the cause of the error. The SOAP envelope included in the HTTP body should consist solely of a SOAP body
element containing a SOAP Fault
element in place of the standard SOAP body format for the call. No other content should be included in the body.
The Fault
element consists of the following sub-elements:
Element | Required | Description |
---|---|---|
faultcode | Yes | Contains a string identifying the error |
faultstring | Yes | Contains a human-readable description of the error. |
detail | No | Provides additional detail about the error in any format according to the SOAP specification. |
faultactor (no longer used) | No | Contains information about the cause of the error, but is ignored by SMAPI. |
The expected syntax for the Fault
element is:
<[soap]:Fault>
<faultcode>[errorCode]</faultcode>
<faultstring>[errorDescription]</faultstring>
<detail>[errorDetails]</detail>
</[soap]:Fault>
The expectations for these values within Sonos are described in the sections below.
Sonos authentication errors
Sonos authentication errors have different requirements than general errors. See Handle auth errors for details.
Fault codes
The faultcode
element contains a defined fault code indicating the type of error encountered. Sonos defines about a dozen predefined codes your music service should use. SOAP defines several types of errors of which Sonos uses two: Client and Server. Server errors within SMAPI typically indicate an issue with your music service such as a planned outage and are also used for the default error case when none of the other defined fault codes fits the situation (even if the problem is clearly not in your music service). Client errors indicate that the server is operational but a particular request cannot be fulfilled for one of the defined reasons. Some of the reasons to throw a Client error include problems authenticating a user, users trying to access functionality not available to their account type or location, and incorrect or invalid ID values that do not map to valid items in the music service.
The format of the faultcode
element is as follows:
[errorType].[codeString]
The errorType
is either Client or Server and codeString
is the actual error code.
Sonos supports the following fault codes:
Fault code | Type | Meaning |
---|---|---|
ServiceUnavailable | Server | The server is temporarily unavailable. Typically this is thrown for a planned outage or when the reason for an unplanned outage is understood and the service has enough connectivity to return a response. |
ServiceUnknownError | Server | An unknown error occurred. This is the default error for most services and is thrown for any error without a specific alternate exception defined. |
AuthTokenExpired | Client | The request has an invalid token. The most likely reason for this error is an expired token. See the refreshing expired authentication tokens section of Use authentication tokens for details. |
DeviceCertExpired | Client | The provided device certificate has expired. |
DeviceCertInvalid | Client | The provided device certificate is invalid. |
DeviceCertRequired | Client | A required device certificate was not provided. |
DeviceCertRevoked | Client | The provided device certificate is revoked by the service. |
DeviceLimit | Client | This user account has reached the limit for concurrent account use with your service. |
ItemNotFound | Client | The requested item does not exist. If the correct ID was sent by the request, the related item may have been deleted via a different client. |
LoginDisabled | Client | The user’s account has been disabled. |
LoginInvalid | Client | The username/password combination was invalid. |
LoginUnauthorized | Client | The user’s account can no longer be used on Sonos. This should be sent if a trial account expired. |
LoginUnsupported | Client | The user’s account cannot be used on Sonos or with the specified feature. This should be sent if you require a specific service tier to use Sonos or to use specific features and the requesting user's account is on a different service tier. |
NOT_LINKED_RETRY | Client | The user account is not linked to the supplied link code but is linkable. This error is only used as part of the DeviceLink authentication process and is not user visible in any way. See getDeviceAuthTokenfor details. |
NOT_LINKED_FAILURE | Client | The user account cannot be linked to the supplied code or the code is invalid. This indicates a permanent failure. Sonos must request a new link code for the user. This error is only used as part of the DeviceLink authentication process and is not user visible in any way. See getDeviceAuthTokenfor details. |
SessionIdInvalid | Client | The supplied session ID is invalid or has expired. We recommend that you no longer use getSessionId. |
TokenRefreshRequired | Client | The token has expired but can be refreshed. This error must include a detail element containing a new token and a new refresh token for the user. No error message is displayed to the user but the supplied new token replaces the existing token information for the user cached in the controller. |
UnsupportedTerritory | Client | The request is coming from outside the geographic range supported by your service according to whatever means you use to determine user location (registered location of the user, geographic location of the IP address, etc.). If using session-based authentication, the getSessionId call will return this error when applicable. If using DeviceLink authentication, it will not be returned until the first call that uses an established authentication token. Calls to getDeviceLinkCode and getDeviceAuthToken will succeed whether or not any geographic constraints are met. |
Logging
Sonos logs all errors thrown by your music service. Errors that happen while actively streaming music are logged in the player; all other errors including errors while setting up accounts, logging in, browsing, or searching are logged in the controller. In addition to the fault code, the contents of the faultstring
element are stored in the log for future reference. The faultstring
element should contain a human-readable description of the error as well as any information you find helpful for debugging cases when the error is thrown. These logs can then be accessed using diagnostic programs if necessary for troubleshooting.
Desktop controller logs will also feed into the Mac OS X Console viewer or can be found as XML files on Windows at:
[systemdrive\]:\\programdata\\Sonos,\_Inc\\runtime
In this example, systemdrive
is your main system drive, typically c. Note that this is a hidden directory and also that you will need to add a pair of matching opening and closing elements to these files to view them in an XML viewer (any element name is fine; <foo>
at the start of the file and </foo>
at its end will work).
Default error messages
Sonos uses the fault code you return and the current state of the controller to determine the error message to show users when an error is thrown. Default text is defined for each of the supported fault codes in several applicable situations such as setting up your music service, browsing music, or streaming music.
For instance, suppose a user had a trial account for your music service that just expired. Sonos still has a valid authentication token for the user and sends a request to browse your service using that token.
The request should result in a Client.LoginUnauthorized fault and the following error message will display to the user:
Unable to browse music - your [serviceName] trial has expired.
The [serviceName] is the name of your music service.
On the back-end, the following request was made by the controller to your service:
POST <http://musicservice.example.com>
Accept-Encoding: gzip,deflate
Content-Type: text/xml;charset=UTF-8
SOAPAction: "<http://www.sonos.com/Services/1.1#getMetadata>"
Host: example.com
<soap:Envelope
xmlns:soap="<http://schemas.xmlsoap.org/soap/envelope/>"
xmlns:ns="<http://www.sonos.com/Services/1.1">>
<soap:Header>
<ns:credentials>
<ns:deviceId>device1</ns:deviceId>
<ns:deviceProvider>Sonos</ns:deviceProvider>
<ns:loginToken>
<ns:token>authtoken</ns:token>
<ns:key>refreshtoken</ns:key>
<ns:householdId>house1</ns:householdId>
</ns:loginToken>
</ns:credentials>
</soap:Header>
<soap:Body>
<ns:getMetadata>
<ns:id>albums-album123</ns:id>
<ns:index>0</ns:index>
<ns:count>10</ns:count>
</ns:getMetadata>
</soap:Body>
</soap:Envelope>
And you should send the following response:
HTTP/1.1 500 Internal Server Error
Content-Type: text/xml; charset=utf8;
Content-Length: 320
<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope
xmlns:soap="<http://schemas.xmlsoap.org/soap/envelope/>"
xmlns:xsi="<http://www.w3.org/2001/XMLSchema-instance>"
xmlns:xsd="<http://www.w3.org/2001/XMLSchema">>
<soap:Body>
<soap:Fault>
<faultcode>Client.LoginUnauthorized</faultcode>
<faultstring>Trial account has expired</faultstring>
</soap:Fault>
</soap:Body>
</soap:Envelope>
Status code 500
Note that the HTTP status code returned is 500 even though the fault code is classified as a client error.
The following table lists the error messages that will be presented to a Sonos user under different usage contexts. The Sonos app replaces the [variable] text with the appropriate content.
Error code | Message shown if fault happens during browse/search | Message shown if fault happens during account set-up | Message shown if fault happens during streaming |
---|---|---|---|
LoginInvalid | Unable to browse music - your [variable] login information is not valid. | N/A | Unable to play [variable] - the [variable] account login information is not valid. |
LoginDisabled | N/A | N/A | N/A |
LoginUnauthorized | Unable to browse music - your [variable] trial has expired. | N/A | Unable to play [variable] - your [variable] trial has expired. Please upgrade your account with [variable]. |
LoginUnsupported | Unable to browse music - your [variable] account has not been upgraded to a subscription account. | There was a problem adding this account. To use this account with Sonos, you must first upgrade it with [variable] to become a full subscriber. | Unable to play [variable] - please upgrade your account with [variable] to become a full subscriber. |
DeviceLimit | N/A | N/A | N/A |
UnsupportedTerritory | N/A | N/A | N/A |
SessionIdInvalid | Unable to browse music. (We silently try to reauthenticate if this error comes up, and only fail if that reauth attempt fails.) | N/A | N/A |
ItemNotFound | Unable to browse music. -or- There was a problem searching. Please try again. | N/A | N/A |
Default error message | Unable to browse music. | The [variable] server did not recognize your login information. Please make sure that your login (email address or username), and your password are correct, and try again. If the problem persists, please contact [variable] for help with your account. | Unable to play [variable] - the connection to [variable] was lost. |
AuthTokenExpired | Displays the reauthorization wizard for the account that’s attempting to browse. | N/A | N/A |
Custom error messages
You must use one of the defined fault codes for all error messages, but you may supply a custom error message instead of using the default error message associated with that fault code. Sonos allows you to override any default error message, but please exercise caution if you choose to override messages that direct users to action. For example, think carefully before changing the error message that tells users to reauthenticate with your service when necessary.
Custom error messages are specified using the detail element of a SOAP fault by including two sub-elements: ExceptionInfo
and SonosError
:
ExceptionInfo
- Contains additional logging information specific to your error. Its contents are logged alongside the contents of thefaultcode
andfaultstring
elements and available for debugging issues, should they arise.SonosError
- Contains a numeric code between 0 and 999. Each code maps to an entry in your application’s Localization Resource section with a property key ofError[sonosErrorValue]Message
with the actual error message being the corresponding property value. Messages have a limit of 125 characters and must be provided in each of the languages supported by Sonos.
The expected syntax for the detail element is:
<detail>
<[ns]:ExceptionInfo>[logMessage]<[ns]:ExceptionInfo>
<[ns]:SonosError>[sonosErrorValue]<[ns]:SonosError>
</detail>
The [logMessage] is a string placed into the error logs and [sonosErrorValue] is the numerical key to the error message stored in your localization resource of choice. In the i18 file, you must have a property key with the format of Error[sonosErrorValue]Message
. You should also have a key-value pair for this error message in every language you support.
For example, suppose your service restricts rating songs to premium members. When a member with a free account tries to rate a song, he might get the following error:
Rating is only available to premium members.
The underlying rateItem call might return the following response:
HTTP/1.1 500 Internal Server Error
Content-Type: text/xml; charset=utf8;
Content-Length: 360
<soap:Envelope
xmlns:soap="<http://schemas.xmlsoap.org/soap/envelope/>"
xmlns:ns="<http://www.sonos.com/Services/1.1">>
<soap:Body>
<soap:Fault>
<faultcode>Client.LoginUnsupported</faultcode>
<faultstring>Unsupported action for account type
</faultstring>
<detail>
<ns:ExceptionInfo>Feature Unsupported for User Type
</ns:ExceptionInfo>
<ns:SonosError>27</ns:SonosError>
</detail>
</soap:Fault>
</soap:Body>
</soap:Envelope>
And the i18 file will include the following entries:
{
"en-US":{
"common":{...},
"integration":{
"Error27Message":"Rating is only available to premium members.",
}
},
"de-DE":{
"common":{...},
"integration":{
"Error27Message":"Bewertung ist nur fur Premium Mitglieder verfugbar.",
}
},
},
If for some reason your Localization Resource does not have the required messages, the user will get an error message indicating something went wrong and they should retry. If the issue is not temporary, this could result in a loop until the user gives up.
Updated 3 months ago