Posted in:

In serverless architectures, it’s common to build your website as a SPA, meaning that you only need static website hosting. A common choice for this is Amazon S3, but if you have an Azure subscription, you may be wondering if you can use Azure Blob Storage instead.

Well, if you create a Blob Storage Account, and make a container and set it’s blobs to be publicly accessible, then you can navigate to your site by visiting a URL like: https://mystorageaccount.blob.core.windows.net/mycontainer/index.html

And this works just fine, but there are a few key limitations you need to be aware of.

First of all, although you can point a custom domain at an Azure Blob Storage account, you can’t upload your own SSL certificate. This is the top requested feature for Azure Blob Storage, and Microsoft’s response indicates they do intend to resolve this as a high priority.

Second of all, we’d rather not need to specify index.html explicitly, but Azure Blob storage doesn’t have default document support. This is another highly requested feature and so hopefully Microsoft will also address this soon, along with removing the need to specify the container name in the URL.

And there are a few other features that are desirable for a static website host, such as the ability to serve a custom 404 page.

So in its current state, Azure Blob Storage isn’t ideal for hosting a static website.

Fortunately, there is now a workaround available in the shape of Azure Functions proxies. What you can do is create an Function App and give it a proxy that passes on requests to Blob Storage.

Let’s see how to do that. In our function app, because it’s still in preview, we need to explicitly enable proxies:

image

And I’ll create two proxies. The first, will redirect the base URL to the index.html in my static hosting blob container:

image

And the second will forward every additional request for any other path directly to the blob container. That’s achieved with the special {*restOfPath} syntax which matches any path.

image

With that in place, I now can directly access my static website by visiting the URL of the function app.

What’s more, Azure Function apps support custom domains, so I can go in and configure some domain name I own to point at the function app.

image

Azure Function Apps also allow you to upload SSL certificates, so as well as solving the default document issue, and removing the need for the container name in the path, this also is a way to use HTTPS on custom domains. So with Azure Functions proxies you can work around most of the major limitations of static hosting on Azure Blob Storage.

Obviously you will pay for a function execution for each file that’s requested, but remember that you get 1 million free function executions a month, so you may not end up paying anything for most websites.

Want to learn more about how to build serverless applications in Azure? Be sure to check out my Pluralsight courses Building Serverless Applications in Azure and Microsoft Azure Developer: Create Serverless Functions

Comments

Comment by Maringa Manguyu

worked a treat!

Maringa Manguyu
Comment by rorz0r

You are a legend (among cheapskates like me)

rorz0r
Comment by Wayne Massey

Good stuff.. thank you!! just to point for others out its {*restOfPath} (with asterisk) in the Route Template and {restOfPath} (w/o asterisk) in the Backend Url. I glanced over that difference and used {*restOfPath} for both and wasted a few cycles wondering why I was getting "The resource you are looking for has been removed, had its name changed, or is temporarily unavailable"

Wayne Massey
Comment by Ronald Nieuwenhuis

Hi, great read. Do you have a sugestion to implement a custom 404? now I get a blognotfound returned from my blog storage. Like to handle that to my custom <blob>/404.html

Ronald Nieuwenhuis
Comment by Mark Heath

the good news is that at BUILD they showed a feature for custom default and 404 pages in blob storage. It think might still be in preview/beta, but this is something we're very close to now

Mark Heath
Comment by Mark Heath

I've not tried that yet, but it's probably a better solution for a real-world website. The proxies approach I show here is OK, but can suffer from cold-start issues which might be an issue with some websites.

Mark Heath
Comment by Daniel O'Brien

Just to be clear - the Static Website feature just buys you the default document and 404 redirect. You still need an Azure Function Proxy or Azure CDN to get SSL with a custom domain. So just curious if you recommend one over the other.

Daniel O'Brien
Comment by Mark Heath

With function proxies, its a nice simple, self-contained solution, but with the down-side of potential cold start issues. With the CDN, you're possibly paying a bit more, but you've presumably got faster performance especially if your website visitors are worldwide. So it's a tradeoff you need to choose based on your website requirements.

Mark Heath
Comment by Daniel O'Brien

Got it - thanks for the information! Very helpful blog post and am enjoying your PluralSight courses!

Daniel O'Brien
Comment by Karim Kameka

I have implemented a ReactJS site hosted using the method above and we can get the site to be served via the proxy. The issue we have is we are using OAuth Authentication and the URL Redirect for OAuth provider adds a "/redirect" route to our path. What seems to be happening is that the "/redirect" path is being interpreted as a blob path and we get "Blob not found" has anyone run into this and/or a resolution?

Karim Kameka
Comment by Chandan B

I solved it by adding error page as index.html in the static website section. Are you still facing this issue

Chandan B
Comment by Oliver

Cool! Can you please elaborate on what type of Azure storage account we need for this? (General purpose v1, v2, ....)?

Oliver
Comment by Mark Heath

either is fine

Mark Heath