Manually uploading Assets

This guide will use a curl & NodeJS example to upload data into your project.

The Workflow

To get an asset manually from your hard-drive or from an external URL into GraphCMS, we need to follow 3 steps:

  1. Send the asset to Filestack using our API Key and our stage name.
  2. Receive the response from Filestack which includes the unique handle, size, url etc.
  3. Send a createAsset mutation to your project endpoint to link the image.

Setup - API Key

Before we can get started with uploading we need to retrieve the API Key from our Management API.

To do this, head to the API Explorer in your project. At the top, there is a dropdown right next to the "Prettify" button. If you click it you can select "Management API".

Now paste in the following query, placing PROJECT_ID with the ID that you find in your URL.

    viewer {
        project(id: "PROJECT_ID") {
            stage(name: "master") {
                assetConfig {

If you are using multiple stages, you will also need to replace stage(name:"master") with the stage you want to work with. If you are not using staging, don't worry about it!

You can see all the stage names that are available with this query (also needs to be run against the Management API):

    viewer {
        project(id: "6fbda0ba20a84b188d9ebe17a4d50f16") {
            stages {

Press the big play button and you should retrieve your API Key!

Sending the Asset to Filestack

Please always make sure to prepend a random ID to the filename part of the path of the asset you are uploading.

To generate a unique random ID, you can use a package like uniqid

We will use curl for this example, but you should be able to use the information to accomplish the same in almost any framework.

The endpoint we will be talking to looks like this:

Again, notice the RANDOMID part here, right before the filename. This is very important, as you otherwise might overwrite assets with the same filename. This is only an issue when you upload the files via the Filestack API.


Here is an example URL that I used (the API Key is fake here):

Handy curl Commands

File from Hard-Drive

For sending a file from your hard-drive, the command would look like this:

curl -X POST -F 'fileUpload=@"<filename with ending or path>"' ""

Filled out it will look like this:

curl -X POST -F 'fileUpload=@"logo.png"' ""

File from external URL

For sending an image from an external URL the curl will look like this:

curl -X POST -d url="<url where image is already hosted>" ""

Receiving the Response

If the curl you used went through successfully, you will get a response like this:

  "container": "gcms-prod-eu-west-1",
  "url": "",
  "filename": "logo.png",
  "key": "5cb80469f4fe4e3b8d94b868710415e6-master/30mwfxcuk56k1bwl_logo.png",
  "type": "image/png",
  "size": 101824

The url still points to In the next step when will only need the last part of that URL, which is called the handle. The URL will then be computed on the server to be

Linking the Image to GraphCMS

We now need to run a mutation against our project API to link the image in Filestack with GraphCMS. In the API Explorer, use the dropdown at the top and select Stage: master or any other that you used for uploading the Asset.

To run the createAsset mutation we now need the data that Filestack sent us. First thing is the handle. which is the last part of the url parameter, rHRHnMUyRo6HM1OCZjN1 in this case. We also need the filename, size and type which is the mimeType in the mutation. The filename doesn't need to contain the random ID here.

This is how it could look like:

mutation uploadAsset {
        data: {
            handle: "rHRHnMUyRo6HM1OCZjN1"
            fileName: "logo.png"
            size: 101824
            mimeType: "image/png"
            status: PUBLISHED
    ) {

The response will be:

    "data": {
        "createAsset": {
            "id": "cjncvs9rnlybr0932wg1ha85y",
            "url": ""

Finishing up

Now we have the URL to access our Asset and we are able to see it in our Asset View!

We use Filestack as our Asset Provider. They also offer a React Component that should make uploading images way easier.


We also created a little node script to show you how an uploading scenario might look like. This script uses placeholder images, that are already hosted somewhere. You can apply the same logic to upload images from your hard drive.

Upload Node Script Example