Skip to content

Instantly share code, notes, and snippets.

Embed
What would you like to do?
Setting up CORS on Google Cloud Storage: An unofficial quick start guide to serving web fonts from Google's cloud. (I'm sure a lot of this info could be improved... Please leave comments if you have tips/improvements.)
<?xml version="1.0" encoding="UTF-8"?>
<CORSConfiguration xmlns="http://s3.amazonaws.com/doc/2006-03-01/">
<CORSRule>
<AllowedOrigin>*</AllowedOrigin>
<AllowedMethod>GET</AllowedMethod>
<AllowedMethod>POST</AllowedMethod>
<AllowedMethod>HEAD</AllowedMethod>
<MaxAgeSeconds>2592000</MaxAgeSeconds>
<ExposeHeader>Content-Length</ExposeHeader>
<ExposeHeader>Date</ExposeHeader>
<ExposeHeader>ETag</ExposeHeader>
<ExposeHeader>Access-Control-Allow-Origin</ExposeHeader>
<ExposeHeader>Connection</ExposeHeader>
<AllowedHeader>*</AllowedHeader>
<AllowedHeader>Host</AllowedHeader>
</CORSRule>
</CORSConfiguration>
<?xml version="1.0" encoding="UTF-8"?>
<CorsConfig>
<Cors>
<Origins>
<Origin>*</Origin>
</Origins>
<Methods>
<Method>GET</Method>
<Method>POST</Method>
<Method>HEAD</Method>
</Methods>
<ResponseHeaders>
<ResponseHeader>*</ResponseHeader>
</ResponseHeaders>
<MaxAgeSec>86400</MaxAgeSec>
</Cors>
</CorsConfig>

Login:

Google Cloud Storage

You'll want to login using an official Google account (i.e. if this is for your company, use the comapany Gmail account vs. a personal one.)

When logging in, you might be prompted to verify the account; if so, enter your cell number to get a verification e-mail or phone call.

Once verified, you'll have to agree to the terms of service; do that, and click continue.

Create a project:

Create a new project; here's an example project name:

Acme Co. Web Fonts

You'll then be directed to the "Welcome to Google Cloud Console" page.

Under "Cloud products", click "Go to Cloud Storage" under the "Cloud Storage" header.

You'll be taken to a URI that looks like so:

https://code.google.com/apis/console

Once there, you'll see this message:

"Google Cloud Storage is not active on this project"

Click the big blue "Enable" button.

Next, you'll see this message:

"You must sign up for billing before you will be able to create any buckets."

Google Cloud Storage Pricing:

Google Cloud Storage: Pricing and Support

Setup billing:

Click on the "Billing" link.

Click "Enable Billing" and setup your "Billing Profile".

Follow the instructions.

Create a bucket:

Once billing has been setup, continue on to the Google Cloud Storage Manager.

Create a new bucket by clicking the "New Bucket" button in top-right of interface.

If you're planning on setting up a CNAME for your bucket, you'll want to follow this naming convention:

fonts.acmecompany.com

Upload content:

Once you've created your bucket, upload your web fonts and related assets.

Note: For every file you want to share publicly, click the "Share Publicly" check mark in the file list view of the Google Cloud Storage Manager.

Setup CNAME:

Next, create your CNAME:

fonts.acmecompany.com CNAME c.storage.googleapis.com

Where fonts.acmecompany.com is your bucket name and c.storage.googleapis.com is the host endpoint.

Install and configure the API:

Now, download the gsutil Python API to your Mac.

Read these docs:

Google Cloud Storage: Install gsutil

Google Cloud Storage: gsutil Tool

Tip: use $ gsutil config -b and follow the instructions.

Once installed, and configured, you can access your bucket via the terminal shell.

Create CORS file:

Next, setup a CORS file:

Google Cloud Storage: Cross-Origin Resource Sharing (CORS)

<?xml version="1.0" encoding="UTF-8"?>
<CorsConfig>
  <Cors>
		<Origins>
			<Origin>*</Origin>
		</Origins>
		<Methods>
			<Method>GET</Method>
			<Method>POST</Method>
			<Method>HEAD</Method>
		</Methods>
		<ResponseHeaders>
			<ResponseHeader>*</ResponseHeader>
		</ResponseHeaders>
		<MaxAgeSec>86400</MaxAgeSec>
	</Cors>
</CorsConfig>

Set CORS file:

In terminal, get the CORS:

$ gsutil getcors gs://fonts.acmecompany.com/

Setting CORS:

$ gsutil setcors cors.xml gs://fonts.acmecompany.com/

Interesting info here:

Http Header Vary: Origin causes cache fail in Internet Explorer in Google Cloud Storage

Example usage:

$ gsutil setcors ~/Desktop/cors.xml gs://fonts.acmecompany.com
Setting CORS on gs://fonts.acmecompany.com/...
$ gsutil getcors gs://fonts.acmecompany.com
<?xml version="1.0" ?>
<CorsConfig>
    <Cors>
        <Origins>
            <Origin>
                *
            </Origin>
        </Origins>
        <Methods>
            <Method>
                GET
            </Method>
            <Method>
                POST
            </Method>
            <Method>
                HEAD
            </Method>
        </Methods>
        <ResponseHeaders>
            <ResponseHeader>
                *
            </ResponseHeader>
        </ResponseHeaders>
        <MaxAgeSec>
            86400
        </MaxAgeSec>
    </Cors>
</CorsConfig>

Some more info here:

Google Cloud Storage: Request Body Elements for CORS

Website configuration:

Now, we need to setup index.html and 404.html files:

Google Cloud Storage: Website Configuration

Set default index and 404 error pages:

$ gsutil setwebcfg -m index.html -e 4xx.html gs://fonts.acmecompany.com

@TODO:

  • Figure out how to set caching on uploaded files.
  • Other optiomizations?

Discussions:


Related Gists:


Bonus:

If you need to connect to multiple Google Cloud Storage acounts (say, a work and personal account), you'll need to setup a .boto file for each account.

Here's how I did it:

Run $ gsutil config -b (from steps above) for each Google Cloud Storage account; afterwords, you'll find a ~/.boto and a ~/.boto.bak file (the latter being the .boto file from the first time you ran the config setup). Re-name ~/.boto.bak to something more useful (like .boto-other) then you can add this line to your ~/.bash_profile:

alias gsutil-other=BOTO_CONFIG=$HOME/.boto-other\ gsutil

Now you can run (for example):

$ gsutil-other getcors gs://fonts.personal-site.com/

... and:

$ gsutil getcors gs://fonts.work-site.com/

More information can be found here:

@pipwerks

This comment has been minimized.

Copy link

pipwerks commented Mar 4, 2014

Thanks for the write up, it helped. The info is a bit out of date now. One thing that really tripped me up is the syntax for the gsutil.

The example you provided:

gsutil setcors cors.xml gs://fonts.acmecompany.com/

What I actually needed to type (as of March 2014):

gsutil cors set ~/Desktop/cors.xml gs://bucketname

Two big changes here. The first is a new gsutil syntax: gsutil cors set in place of gsutil setcors. The second is the bucket URL. Your example uses a custom domain name, which I'm not using, so I was trying to use storage.googleapis.com/bucketname but kept getting errors. Turns our you just need to specify the bucket name without the fully qualified URL; if your bucket is named foobar, you wouldn't type gs://storage.googleapis.com/foobar, you'd just type gs://foobar/

The bit about ~/Desktop/cors.xml is simply illustrating the file path to my cors.xml file.

@iamchriswick

This comment has been minimized.

Copy link

iamchriswick commented Jul 21, 2015

Google now recommend that we use json instead of xml

@iamchriswick

This comment has been minimized.

Copy link

iamchriswick commented Jul 21, 2015

Google also recommend that we use json instead of xml:

[
  {
    "origin": ["http://origin1.example.com"],
    "responseHeader": ["Content-Type"],
    "method": ["GET"],
    "maxAgeSeconds": 3600
  }
]
@pesterhazy

This comment has been minimized.

Copy link

pesterhazy commented Oct 11, 2017

Yes, if you're dealing with webfonts, @iamchriswick's suggestion and gsutil cors set gcloud-cors-config.json gs://your-bucket is all you need

@SkydGit

This comment has been minimized.

Copy link

SkydGit commented Jan 26, 2018

Hello.
Excuse me @mhulse, but I don't understand this point :

Next, create your CNAME:
fonts.acmecompany.com CNAME c.storage.googleapis.com
Where fonts.acmecompany.com is your bucket name and c.storage.googleapis.com is the host endpoint.

I don't undestand c.storage.googleapis.com is the host endpoint
Could you explain or give me a sample about it please ? with your example, it's
fonts.acmecompany.com CNAME fonts.acmecompany.com.storage.googleapis.com ??

Thank you for your help.

@NDMCreative

This comment has been minimized.

Copy link

NDMCreative commented May 30, 2018

"c" is the bucket name so if your bucket was call my-bucket the public url for a file might be https://storage.googleapis.com/my-bucket/image.jpg therecore you would use my-bucket.storage.googleapis.com

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.