To license and download media with the API, you need:

You must be aware of what license types your subscription or subscriptions provide so you use the correct license and subscription and download the correct media:

  • Some license types allow you to redownload the media later and others don't.
  • Different license types allow you to download different media sizes. For example, a footage standard-definition subscription allows you to license and download standard-definition videos, but not high-definition videos. A footage high-definition subscription allows you to license and download high-definition videos, but not necessarily standard-definition videos.
  • Different licenses permit different uses. For example, both standard and enhanced image licenses allow royalty-free use of an asset, but the standard license allows only 500,000 print runs and advertising impressions, while the enhanced license allows unlimited runs and impressions.

When you request a license with the API, it provides platform licenses for media. These platform licenses allow different uses of assets than the standard and enhanced licenses. For example, platform licenses can be used to resell media licenses or to use media in places such as applications, web sites, mobile apps, and social media . For details about what you can do with platform licenses, see Shutterstock API Terms of Service.

To get information about your subscriptions and the licenses and media types that they provide, send a request to the GET /v2/user/subscriptions endpoint, with your access token in place of the environment variable SHUTTERSTOCK_API_TOKEN, as in this example:

cURL

curl -X GET 'https://api.shutterstock.com/v2/user/subscriptions' \
-H "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN"

PHP

$options = [
  CURLOPT_URL => "https://api.shutterstock.com/v2/user/subscriptions",
  CURLOPT_USERAGENT => "php/curl",
  CURLOPT_HTTPHEADER => [
    "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN"
  ],
  CURLOPT_RETURNTRANSFER => 1
];

$handle = curl_init();
curl_setopt_array($handle, $options);
$response = curl_exec($handle);
curl_close($handle);

$decodedResponse = json_decode($response);
print_r($decodedResponse);

JavaScript

const sstk = require("shutterstock-api");

sstk.setAccessToken(process.env.SHUTTERSTOCK_API_TOKEN);

const usersApi = new sstk.UsersApi();
usersApi.getUserSubsciptionList()
  .then(({data}) => {
    console.log(data);
  })
  .catch((error) => {
    console.error(error);
  });

The response includes the subscription ID and the formats that it provides:

{
  "id": "s14519612",
  "license": "standard",
  "description": "Images On Demand",
  "formats": [
    {
      "size": "huge",
      "format": "jpg",
      "media_type": "image",
      "min_resolution": 4000000,
      "description": "Huge"
    },
    {
      "size": "medium",
      "format": "jpg",
      "media_type": "image",
      "min_resolution": 1000,
      "description": "Med"
    },
    {
      "size": "supersize",
      "format": "jpg",
      "media_type": "image",
      "min_resolution": 16000000,
      "description": "Super"
    },
    {
      "size": "small",
      "format": "jpg",
      "media_type": "image",
      "min_resolution": 500,
      "description": "Small"
    },
    {
      "size": "vector",
      "format": "eps",
      "media_type": "image",
      "description": "Vector"
    }
    ]
}

Licensing media

To request a license and download media, pass the media ID and the subscription ID to the appropriate endpoint. For example, to license images, use the POST /v2/images/licenses endpoint, as in the following examples. Use your subscription ID for the SUBSCRIPTION_ID environment variable.

If you are using an API subscription from developers.shutterstock.com, you can leave out the subscription ID field in your licensing request. In this case, the API uses the subscription that is linked to the account in the token. If that account has more than one API subscription, it uses the subscription that is closest to its expiration date. Also, API subscriptions can license only one image per request.

If you are using an API subscription, you must include the price and metadata.customer_id fields in the request body, as in the following examples. These fields are for resellers to record their customer's ID and the floating-point price that they charged to the customer, within the restrictions of their revenue-sharing agreement. If you are not reselling the media, you can pass any string in the customer_id field and 0 in the price field.

cURL

DATA='{
  "images": [
    {
      "image_id": "59656357",
      "price": 12.50,
      "metadata": {
        "customer_id": "12345"
      }
    }
  ]
}'

curl -X POST "https://api.shutterstock.com/v2/images/licenses?subscription_id=$SUBSCRIPTION_ID" \
-H "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN" \
-H 'Content-Type: application/json' \
-d "$DATA"

PHP

$body = [
  "images" => [
    [
      "image_id" => "539753938",
      "price"=> 12.50,
      "metadata"=> [
        "customer_id"=> "12345"
      ]
    ]
  ]
];
$encodedBody = json_encode($body);

$options = [
  CURLOPT_URL => "https://api.shutterstock.com/v2/images/licenses?subscription_id=$SUBSCRIPTION_ID",
  CURLOPT_CUSTOMREQUEST => "POST",
  CURLOPT_POSTFIELDS => $encodedBody,
  CURLOPT_USERAGENT => "php/curl",
  CURLOPT_HTTPHEADER => [
    "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN",
    "Content-Type: application/json"
  ],
  CURLOPT_RETURNTRANSFER => 1
];

$handle = curl_init();
curl_setopt_array($handle, $options);
$response = curl_exec($handle);
curl_close($handle);

$decodedResponse = json_decode($response);
print_r($decodedResponse);

JavaScript

const sstk = require("shutterstock-api");

sstk.setAccessToken(process.env.SHUTTERSTOCK_API_TOKEN);

const imagesApi = new sstk.ImagesApi();

const body = {
  "images": [
    {
      "image_id": "1420458122",
      "price": 12.50,
      "metadata": {
        "customer_id": "12345"
      }
    }
  ]
};

const queryParams = {
  "format": "jpg",
  "size": "huge",
  "subscription_id": process.env.SUBSCRIPTION_ID
};

imagesApi.licenseImages(body, queryParams)
  .then(({ data }) => {
    console.log(data);
  })
  .catch((error) => {
    console.error(error);
  });

The response includes a download link for each piece of media:

{
  "data": [
    {
      "image_id": "59656357",
      "download": {
        "url": "https://download.shutterstock.com/gatekeeper/[random-characters]/shutterstock_59656357.jpg"
      },
      "allotment_charge": 1
    },
    {
      "image_id": "1079756147",
      "download": {
        "url": "https://download.shutterstock.com/gatekeeper/[random-characters]/shutterstock_1079756147.jpg"
      },
      "allotment_charge": 1
    }
  ]
}

To license editorial media, you must acknowledge the editorial agreement as part of the licensing request. In this case, include "editorial_acknowledgement": true in the request, as in the following example.

cURL

curl -X POST "https://api.shutterstock.com/v2/images/licenses?subscription_id=$SUBSCRIPTION_ID" \
--header "Authorization: Bearer $ACCESS_TOKEN" \
--header "Content-Type: application/json" \
--data '{
"images": [
  {
    "image_id": "494469670",
    "editorial_acknowledgement": true
  }
  ]
}'

PHP

$body = [
  "images" => [
    [
      "image_id" => "494469670",
      "editorial_acknowledgement" => true
    ]
  ]
];
$encodedBody = json_encode($body);

$options = [
  CURLOPT_URL => "https://api.shutterstock.com/v2/images/licenses?subscription_id=$SUBSCRIPTION_ID",
  CURLOPT_CUSTOMREQUEST => "POST",
  CURLOPT_POSTFIELDS => $encodedBody,
  CURLOPT_USERAGENT => "php/curl",
  CURLOPT_HTTPHEADER => [
    "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN",
    "Content-Type: application/json"
  ],
  CURLOPT_RETURNTRANSFER => 1
];

$handle = curl_init();
curl_setopt_array($handle, $options);
$response = curl_exec($handle);
curl_close($handle);

$decodedResponse = json_decode($response);
print_r($decodedResponse);

JavaScript

const sstk = require("shutterstock-api");

sstk.setAccessToken(process.env.SHUTTERSTOCK_API_TOKEN);

const imagesApi = new sstk.ImagesApi();

const body = {
  "images": [
    {
      "image_id": "170076830",
      "editorial_acknowledgement": true
    }
  ]
};

const queryParams = {
  "subscription_id": process.env.SUBSCRIPTION_ID
  "size": "huge"
};

imagesApi.licenseImages(body, queryParams)
  .then(({data}) => {
    console.log(data);
  })
  .catch((error) => {
    console.error(error);
  });

To determine whether an image is considered an editorial image, look at the value for the model_released field in the image details. Editorial images have a code value of 3 and a translation_id field value of EDITORIAL_ONLY.

To determine whether a video clip is considered an editorial video clip, look at the value for the model_released field in the video details. Editorial videos have a value of editorial.

Licensing sandbox

You can use the licensing sandbox API to test your application's licensing code for images and video and verify that your subscription is working. Audio and editorial licensing are not available in the sandbox. To use the sandbox, change the base URL of your requests to https://api-sandbox.shutterstock.com. If you are using the JavaScript SDK, use the setSandbox method, as in the example in the right-hand pane (requires SDK version 1.0.11 or later).

The licensing sandbox API is exactly like the main API, except that requests to POST /v2/images/licenses or POST /v2/videos/licenses don't deduct credits from your subscription or provide licenses. Requests to POST /v2/audio/licenses and POST /v2/editorial/licenses in the sandbox fail. Instead of providing a license and full-size image or video, these two endpoints provide a preset sample image or video. The response includes an allotment_charge field as usual, but that allotment charge is not deducted from your subscription. All other endpoints in the sandbox API work exactly the same way as the main API.

The sandbox API verifies that the subscription is valid for the licensing request just like the main API. It also returns the same HTTP status codes, so the licensing endpoints return a 200 OK code if the request was valid. The sandbox API uses the same applications and it requires the same authentication and subscriptions as the main API.

These examples show how to test licensing with the sandbox:

cURL

DATA='{
  "images": [
    {
      "image_id": "59656357",
      "price": 12.50,
      "metadata": {
        "customer_id": "12345"
      }
    }
  ]
}'

curl -X POST "https://api-sandbox.shutterstock.com/v2/images/licenses?subscription_id=$SUBSCRIPTION_ID" \
-H "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN" \
-H 'Content-Type: application/json' \
-d "$DATA"

PHP

$body = [
  "images" => [
    [
      "image_id" => "539753938",
      "price"=> 12.50,
      "metadata"=> {
        "customer_id"=> "12345"
      }
    ]
  ]
];
$encodedBody = json_encode($body);

$options = [
  CURLOPT_URL => "https://api-sandbox.shutterstock.com/v2/images/licenses?subscription_id=$SUBSCRIPTION_ID",
  CURLOPT_CUSTOMREQUEST => "POST",
  CURLOPT_POSTFIELDS => $encodedBody,
  CURLOPT_USERAGENT => "php/curl",
  CURLOPT_HTTPHEADER => [
    "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN",
    "Content-Type: application/json"
  ],
  CURLOPT_RETURNTRANSFER => 1
];

$handle = curl_init();
curl_setopt_array($handle, $options);
$response = curl_exec($handle);
curl_close($handle);

$decodedResponse = json_decode($response);
print_r($decodedResponse);

JavaScript

const sstk = require('shutterstock-api');

sstk.setSandbox(true);

sstk.setAccessToken(process.env.SHUTTERSTOCK_API_TOKEN);

const imagesApi = new sstk.ImagesApi();

const body = {
  "images": [
    {
      "image_id": "419235589",
      "price": 12.50,
      "metadata": {
        "customer_id": "12345"
      }
    }
  ]
};

const queryParams = {
  "format": "jpg",
  "size": "huge",
  "subscription_id": process.env.SUBSCRIPTION_ID
};

imagesApi.licenseImages(body, queryParams)
  .then(({ data }) => {
    console.log(data);
  })
  .catch((error) => {
    console.error(error);
  });

Downloading the correct size and format

When you license and download media, you must be careful to license and download the size and format that you want. For each download, you should check these things:

  • Verify that your license allows you to download the size that you want. For example, if you want to download a 4K video, your license must include that size.
  • Verify that the media is available in the size and format that you want to download.
  • Verify that you are downloading the size and format that you want.

For example, assume that you searched for images and found an image that you want to license and download. The results from the GET /v2/images/search endpoint might look like this:

{
  "page": 1,
  "per_page": 20,
  "total_count": 7920866,
  "search_id": "Gu4P5p5iJu868FmHUMSBjg",
  "data": [
    {
      "id": "721943485",
      "aspect": 1.5,
      "assets": {
        "preview": {
          "height": 300,
          "url": "https://image.shutterstock.com/display_pic_with_logo/1879103/721943485/stock-photo-mountain-in-the-cloud-and-fog-721943485.jpg",
          "width": 450
        },
        "small_thumb": {
          "height": 67,
          "url": "https://thumb9.shutterstock.com/thumb_small/1879103/721943485/stock-photo-mountain-in-the-cloud-and-fog-721943485.jpg",
          "width": 100
        },
        "large_thumb": {
          "height": 100,
          "url": "https://thumb9.shutterstock.com/thumb_large/1879103/721943485/stock-photo-mountain-in-the-cloud-and-fog-721943485.jpg",
          "width": 150
        },
        "huge_thumb": {
          "height": 260,
          "url": "https://image.shutterstock.com/image-photo/mountain-cloud-fog-260nw-721943485.jpg",
          "width": 390
        }
      },
      "contributor": {
        "id": "1879103"
      },
      "description": "Mountain in the cloud and fog ",
      "image_type": "photo",
      "media_type": "image"
    }
  ]
}

You can pass the ID of the image to the GET /v2/images/{id} endpoint with the parameter view=full to see the full details about the image, including the sizes that are available. (As a shortcut, you can also pass view=full to the search endpoint, but in this case the amount of data returned can be very large.) In this case, the image is available in several sizes of JPG format. With this information, you can verify that the media is licensable in the resolution that you want. You can also check for model releases and other details that affect how you can license and use the media.

{
  "id": "547233985",
  "added_date": "2017-01-02",
  "aspect": 1.5264,
  "assets": {
    "medium_jpg": {
      "display_name": "Med",
      "dpi": 300,
      "file_size": 595968,
      "format": "jpg",
      "height": 655,
      "is_licensable": true,
      "width": 1000
    },
    "huge_tiff": {
      "display_name": "Huge",
      "dpi": 300,
      "file_size": 49686696,
      "format": "tiff",
      "height": 3294,
      "is_licensable": false,
      "width": 5028
    },
    "small_jpg": {
      "display_name": "Small",
      "dpi": 300,
      "file_size": 174080,
      "format": "jpg",
      "height": 328,
      "is_licensable": true,
      "width": 500
    },
    "huge_jpg": {
      "display_name": "Huge",
      "dpi": 300,
      "file_size": 6163456,
      "format": "jpg",
      "height": 3294,
      "is_licensable": true,
      "width": 5028
    },
    "preview": {
      "height": 294,
      "url": "https://image.shutterstock.com/display_pic_with_logo/1603781/547233985/stock-photo-male-and-female-hikers-climbing-up-mountain-cliff-and-one-of-them-giving-helping-hand-people-547233985.jpg",
      "width": 450
    },
    "small_thumb": {
      "height": 66,
      "url": "https://thumb9.shutterstock.com/thumb_small/1603781/547233985/stock-photo-male-and-female-hikers-climbing-up-mountain-cliff-and-one-of-them-giving-helping-hand-people-547233985.jpg",
      "width": 100
    },
    "large_thumb": {
      "height": 98,
      "url": "https://thumb9.shutterstock.com/thumb_large/1603781/547233985/stock-photo-male-and-female-hikers-climbing-up-mountain-cliff-and-one-of-them-giving-helping-hand-people-547233985.jpg",
      "width": 150
    },
    "huge_thumb": {
      "height": 260,
      "url": "https://image.shutterstock.com/image-photo/male-female-hikers-climbing-mountain-260nw-547233985.jpg",
      "width": 398
    }
  },
  "categories": [
    {
      "id": "13",
      "name": "People"
    },
    {
      "id": "18",
      "name": "Sports/Recreation"
    }
  ],
  "contributor": {
    "id": "1603781"
  },
  "description": "Male and female hikers climbing up mountain cliff and one of them giving helping hand.  People helping and, team work concept.\n\n",
  "image_type": "photo",
  "is_adult": false,
  "is_illustration": false,
  "has_model_release": true,
  "media_type": "image",
  "model_releases": [
    {
      "id": "20931733"
    },
    {
      "id": "20931727"
    }
  ],
  "original_filename": "IMG_8407.jpg"
}

To verify that your subscription includes licenses for the size that you want, check the output of the GET /v2/user/subscriptions endpoint, as in the following example. This subscription includes standard licenses for vector, small, and medium images, but not huge image or supersize images or enhanced licenses.

{
  "data": [
    {
      "id": "s12345",
      "expiration_time": "2019-08-27T10:21:10-04:00",
      "license": "standard",
      "description": "Annual Subscription",
      "allotment": {
        "start_time": "2018-08-27T10:21:11-04:00",
        "end_time": "2018-09-27T10:21:10-04:00",
        "downloads_left": 20,
        "downloads_limit": 25
      },
      "formats": [
        {
          "size": "medium",
          "format": "jpg",
          "media_type": "image",
          "min_resolution": 1000,
          "description": "Med"
        },
        {
          "size": "small",
          "format": "jpg",
          "media_type": "image",
          "min_resolution": 500,
          "description": "Small"
        },
        {
          "size": "vector",
          "format": "eps",
          "media_type": "image",
          "description": "Vector"
        }
      ]
    }
  ]
}

When you know that the media is available in the size and format that you want and that your subscription's license coves the correct size, you can download the media in the appropriate size and format. For example, this command licenses and downloads the image in medium JPG format:

cURL

DATA='{
  "images": [
    {
      "image_id": "547233985",
      "format": "jpg",
      "size": "medium",
      "price": 12.50,
      "metadata": {
        "customer_id": "12345"
      }
    }
    ]
  }'

curl -X POST "https://api.shutterstock.com/v2/images/licenses?subscription_id=$SUBSCRIPTION_ID" \
-H "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN" \
-H "Content-Type: application/json" \
-d "$DATA"

PHP

$body = [
  "images" => [
    [
      "image_id" => "547233985",
      "format" => "jpg",
      "size" => "medium",
      "price" => 12.50,
      "metadata" => [
        "customer_id" => "12345"
      ]
    ]
  ]
];
$encodedBody = json_encode($body);

$options = [
  CURLOPT_URL => "https://api.shutterstock.com/v2/images/licenses?subscription_id=$SUBSCRIPTION_ID",
  CURLOPT_CUSTOMREQUEST => "POST",
  CURLOPT_POSTFIELDS => $encodedBody,
  CURLOPT_USERAGENT => "php/curl",
  CURLOPT_HTTPHEADER => [
    "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN",
    "Content-Type: application/json"
  ],
  CURLOPT_RETURNTRANSFER => 1
];

$handle = curl_init();
curl_setopt_array($handle, $options);
$response = curl_exec($handle);
curl_close($handle);

$decodedResponse = json_decode($response);
print_r($decodedResponse);

JavaScript

const sstk = require("shutterstock-api");

sstk.setAccessToken(process.env.SHUTTERSTOCK_API_TOKEN);

const imagesApi = new sstk.ImagesApi();

const body = {
  "images": [
    {
      "image_id": "170076830",
      "format": "jpg",
      "size": "medium",
      "price": 12.50,
      "metadata": {
        "customer_id": "12345"
      }
    }
  ]
};

const queryParams = {
  "subscription_id": process.env.SUBSCRIPTION_ID
};

imagesApi.licenseImages(body, queryParams)
  .then(({data}) => {
    console.log(data);
  })
  .catch((error) => {
    console.error(error);
  });

The result includes a download link for the image in the appropriate size:

{
  "data":
  [
    {"image_id": "547233985",
      "download":
      {
        "url":"https://download.shutterstock.com/gatekeeper/[random-characters]/shutterstock_547233985.jpg"
      },
      "allotment_charge": 1
    }
  ]
}

Request metadata

The licensing request body must include metadata that depends on your subscription type and on the type of media that you are licensing:

API subscriptions

If you are using an API subscription from the API subscription page, you must include the price and metadata.customer_id fields in the request body, as in the following example. These fields are for resellers to record their customer's ID and the floating-point price that they charged to the customer, within the restrictions of their revenue-sharing agreement. If you are using an API subscription and are not reselling the media, you can pass any string in the customer_id field and 0 in the price field.

{
  "images": [
    {
      "image_id": "59656357",
      "price": 22.50,
      "metadata": {
        "customer_id": "12345"
      }
    }
  ]
}

For more information about API subscriptions, see Subscriptions in the API reference.

Enterprise subscriptions

Enterprise partners who are using Premier subscriptions must provide a metadata object on each media item to license. These partners customize their integration to have up to 4 metadata fields for tracking, grouping, or correlating licensing transactions on their invoices. Each integration requires a different set of metadata fields.

In this case, you must pass an empty or non-empty value for each field that your integration requires, as in the following example. To find the metadata fields that are required or optional for your subscription, use the GET /v2/user/subscriptions endpoint.

{
  "images": [
    {
      "image_id": "59656357",
      "metadata": {
        "customer_id": "12345",
        "geo_location": "US",
        "number_viewed": "15",
        "search_term": "dog"
      }
    }
  ]
}

Editorial media licensing

To license editorial media, you must acknowledge the editorial agreement as part of the licensing request. In this case, include "editorial_acknowledgement": true in the request, as in the following example.

To determine whether an image is considered an editorial image, look at the value for the model_released field in the image details. Editorial images have a code value of 3 and a translation_id field value of EDITORIAL_ONLY.

To determine whether a video clip is considered an editorial video clip, look at the value for the model_released field in the video details. Editorial videos have a value of editorial.

{
  "images": [
    {
      "image_id": "494469670",
      "editorial_acknowledgement": true
    }
  ]
}
{
  "images": [
    {
      "image_id": "59656357",
      "price": 22.50,
      "metadata": {
        "customer_id": "12345",
        "geo_location": "US",
        "number_viewed": "15",
        "search_term": "dog"
      }
    }
  ]
}

Downloads under revenue-sharing programs must include the floating-point number final cost to the end customer in the price field. The revenue sharer keeps a percentage of this cost based on its agreement with Shutterstock. This price can not be lower than the price floor for the media asset; if it is, the API changes it to the price floor for the asset.

Subscriptions with comp licenses

Complimentary (comp) licenses are used for testing purposes, unlimited plans, and other special cases. The request for a comp license is the same as for any other type of license, but the resulting license is not always the same. If the subscription is configured for testing purposes and similar cases, the API provides a dummy license. This dummy license does not provide any rights to the customer; it permits customers to view the media without a full license. In this case, the customers have no rights to use the media in any way.

When the API processes a comp license transaction, it does not validate the metadata. Therefore, if you are using comp licenses for testing purposes and your transactions require metadata, you must make sure that the metadata is accurate.

Redownloading media

Most of the time, you download media as soon as you license it, but some subscription types allow you to redownload media later. Shutterstock considers each license to be a unique transaction for a single use of the media, so licensing a media item once does not necessarily mean that you can retrieve it later.

You can use the appropriate endpoint, such as GET /v2/images/licenses, to see your licenses:

cURL

curl 'https://api.shutterstock.com/v2/images/licenses' \
-X GET \
-H "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN"

PHP

$options = [
  CURLOPT_URL => "https://api.shutterstock.com/v2/images/licenses",
  CURLOPT_USERAGENT => "php/curl",
  CURLOPT_HTTPHEADER => [
    "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN"
  ],
  CURLOPT_RETURNTRANSFER => 1
];

$handle = curl_init();
curl_setopt_array($handle, $options);
$response = curl_exec($handle);
curl_close($handle);

$decodedResponse = json_decode($response);
print_r($decodedResponse);

JavaScript

const sstk = require("shutterstock-api");

sstk.setAccessToken(process.env.SHUTTERSTOCK_API_TOKEN);

const imagesApi = new sstk.ImagesApi();

imagesApi.getImageLicenseList()
  .then(({data}) => {
    console.log(data);
  })
  .catch((error) => {
    console.error(error);
  });

The response includes your license information:

{
  "data": [
  {
    "id": "i4117504982",
    "user": {
      "username": "jsmith"
      },
    "license": "standard",
    "subscription_id": "s14565368",
    "download_time": "2018-08-31T14:27:10-04:00",
    "image": {
      "id": "1079756147",
      "format": {
        "size": "huge"
      }
    }
  },
  {
    "id": "i4117504971",
    "user": {
      "username": "jsmith"
      },
    "license": "standard",
    "subscription_id": "s31565368",
    "download_time": "2018-08-31T14:27:10-04:00",
    "image": {
      "id": "59656357",
      "format": {
        "size": "huge"
      }
    }
  }
  ]
}

Then, if your subscription permits redownloads, you can use the license ID to request a new download URL from the POST v2/images/licenses/{license_id}/downloads endpoint, as in this example:

cURL

curl "https://api.shutterstock.com/v2/images/licenses/i4117504982/downloads" \
-X POST \
--header "Authorization: Bearer $ACCESS_TOKEN"

PHP

$body = [];
$encodedBody = json_encode($body);

$options = [
  CURLOPT_URL => "https://api.shutterstock.com/v2/images/licenses/i4152144892/downloads",
  CURLOPT_CUSTOMREQUEST => "POST",
  CURLOPT_POSTFIELDS => $encodedBody,
  CURLOPT_USERAGENT => "php/curl",
  CURLOPT_HTTPHEADER => [
    "Authorization: Bearer $SHUTTERSTOCK_API_TOKEN",
    "Content-Type: application/json"
  ],
  CURLOPT_RETURNTRANSFER => 1
];

$handle = curl_init();
curl_setopt_array($handle, $options);
$response = curl_exec($handle);
curl_close($handle);

$decodedResponse = json_decode($response);
print_r($decodedResponse);

JavaScript

const sstk = require("shutterstock-api");

sstk.setAccessToken(process.env.SHUTTERSTOCK_API_TOKEN);

const imagesApi = new sstk.ImagesApi();

const id = "i7304088111"; // License ID, not image ID

const body = {
  "size": "huge"
};

imagesApi.downloadImage(id, body)
  .then((data) => {
    console.log(data);
  })
  .catch((error) => {
    console.error(error);
  });

The response includes a download link:

{
  "url":"https://download.shutterstock.com/gatekeeper/[random-characters]/shutterstock_1079756147.jpg"
}

Downloading or backing up assets to a CMS or DAM

To populate your content management system (CMS) or digital asset management (DAM) system with your licensed media, you write client code that runs these tasks:

  1. Authenticate using your image purchasing account as usual.
  2. Create a list of the images that you need to download. If your CMS or DAM has a list of images that you have already downloaded, you can use the response from the GET /v2/images/licenses endpoint to get the IDs of licensed images that you have not downloaded. The images in the response are in reverse chronological order, with the most recent download at the top of the list. Therefore, you can page through the results from this endpoint and add each image to the list until you find an image that you have already downloaded. Then, you can stop adding items to the list, because all images past that image are older downloads.
  3. Download the images with one of these methods:
    • Download the image with the download URL that you received when you first licensed the image.
    • If your license permits redownloads, redownload the image with the POST /v2/images/licenses/{license_id}/downloads endpoint. You can tell if you can redownload the image by sending a request to the GET /v2/images/licenses endpoint and including the image ID in the image_id query parameter. If the is_downloadable field in the response is true, you can redownload the image.
    • Relicense the image and get a new download URL. When you have the image, you can rename it before copying the file to your system.
  4. Run this process in batches as needed to keep downloading and copying the previously-licensed images. The process is similar for videos and audio tracks.