'audio tag not working correctly when playing an mp3 stored as azure blob in chrome
We are getting a strange behavior when using Chrome to play an mp3 file stored as a blob in Azure. All other browsers seem to play the track correctly but Chrome does not allow the user to skip to other parts of the track.
To demonstrate this open the following two urls in Chrome - they are both the same track. The first one will let you skip to other sections, the second one won't.
http://scantopdf.eu/downloads/music/igygtrack.mp3
http://igygprodstore.blob.core.windows.net/igyg-site-blobs1/10b1122f-eb43-44fd-aa48-919d8b6955c1.mp3
Is this a Chrome issue or an Azure storage issue? Is there any HTML5 code that will play the blob correctly?
Solution 1:[1]
Here's what's different:
The Azure Blob Storage endpoint does not return Accept-Ranges: Bytes to your browser - that's why you can't seek.
Now if you look closer at the response coming from Azure Storage you'll notice a x-ms-version header with a value that looks ancient:
HTTP/1.1 200 OK
Content-Length: 13686118
Content-Type: audio/mp3
...
x-ms-version: 2009-09-19
Both old and new storage accounts default to the same API version so they don't break backwards compatibility with code out there.
Here's the version history on storage API versions:
https://msdn.microsoft.com/en-us/library/azure/dd894041.aspx
We highly recommend using version 2011-08-18 version and later for scenarios that require quoted ETag values or valid Accept-Ranges response headers, since browsers and other streaming clients require these for efficient download and retries.
Here's how to talk Azure Storage into sending you Accept-Ranges: bytes
You either have to pass in x-ms-version header with a post-August-2011 API version -
$ curl -I -s http://igygprodstore.blob.core.windows.net/igyg-site-blobs1/10b1122f-eb43-44fd-aa48-919d8b6955c1.mp3
HTTP/1.1 200 OK
Content-Length: 13686118
Content-Type: audio/mp3
...
? Note no Accept-Ranges header!
$ curl -I -s -H "x-ms-version: 2015-12-11" http://igygprodstore.blob.core.windows.net/igyg-site-blobs1/10b1122f-eb43-44fd-aa48-919d8b6955c1.mp3
HTTP/1.1 200 OK
Content-Length: 13686118
Content-Type: audio/mp3
...
Accept-Ranges: bytes
or you need to set the default API version at the container level, with something like AzureBlobUtility: https://github.com/Plasma/AzureBlobUtility
C:\AzureBlobUtility\bin\Release>BlobUtility.exe -k fH00xxxxxxxxxx7w== -a baboonstorage1 -c public --setDefaultServiceVersion 2015-12-11
[2016-09-20 01:59:45] INFO Program - Updating API Version from to 2015-12-11
[2016-09-20 01:59:45] INFO Program - Updated Ok
Or, use the Storage SDK to set the default API version at storage account level:
// From http://geekswithblogs.net/EltonStoneman/archive/2014/10/09/configure-azure-storage-to-return-proper-response-headers-for-blob.aspx
var connectionString = "DefaultEndpointsProtocol=https;AccountName={accountName};AccountKey={accountKey}";
var storageAccount = CloudStorageAccount.Parse(connectionString);
var blobClient = storageAccount.CreateCloudBlobClient();
var props = blobClient.GetServiceProperties();
props.DefaultServiceVersion = "2015-12-11";
blobClient.SetServiceProperties(props);
Use curl to make sure your changes are live -
$ curl -I -s https://baboonstorage1.blob.core.windows.net/public/test.mp3
HTTP/1.1 200 OK
Content-Length: 13686118
Content-Type: audio/mpeg
...
Accept-Ranges: bytes
...
x-ms-version: 2015-12-11
Solution 2:[2]
As evilSnobu pointed out, the default version of Azure Blob Storage API doesn't return a Accept-Ranges: Bytes header in the response, which prevents the audio files from being seekable.
You can change the default Blob Storage API version with PowerShell, like this:
$context = New-AzStorageContext `
-StorageAccountName <yourAccount> `
-StorageAccountKey <key>
Update-AzStorageServiceProperty `
-ServiceType Blob `
-DefaultServiceVersion 2021-04-10 `
-Context $context
Note: that requires PowerShell Az module to be installed. You can also use the old AzureRM module, in which case your commands will be New-AzureStorageContext and Update-AzureStorageServiceProperty respectively.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | |
| Solution 2 |
