Upload media

Required authentication scope

Uploading media items to a user’s library or album requires either the .appendonly or the .photoslibrary scope.

Media items can also be created using the .sharing scope. To create items with the .sharing scope, you must first create an album and mark it as shared using shareAlbum. You can then create media items that are shared with the user in the album. You can't create items directly in the user's library or in albums that your app hasn't shared.

When listing albums, the isWriteable property indicates whether your application has access to create media in a particular album.

The upload process

Uploading media items is a two-step process:

  1. Upload the raw bytes to a Google Server. This doesn't result in any media items being created in the user’s Google Photos account. Instead, it returns an upload token which identifies the uploaded bytes.
  2. Use the upload token to create the media item in the user’s Google Photos account. You can choose whether the media should be also added to a specific album. For more information, see Create albums.

Uploading bytes

Bytes are uploaded to Google using a POST request. The POST request must include the binary of the file in the request body and include the following fields in the header:

Header fields
Content-type Set to application/octet-stream.
X-Goog-Upload-File-Name Recommended. Set to the filename along with the file extension. Only the filename is shown to the user in Google Photos.
X-Goog-Upload-Protocol Set to raw.

Here is a POST request header:

POST https://photoslibrary.googleapis.com/v1/uploads
Authorization: Bearer OAUTH2_TOKEN
Content-type: application/octet-stream
X-Goog-Upload-File-Name: FILENAME
X-Goog-Upload-Protocol: raw
MEDIA_BINARY_DATA

If this POST request is successful, an upload token which is in the form of a raw text string, is returned as the response body. To create media items, use these text strings in the batchCreate call.

UPLOAD_TOKEN

The suggested file size for images is less than 50 MB. Files above 50 MB are prone to performance issues.

The Google Photos Library API supports resumable uploads. A resumable upload allows you to split a media file into multiple sections and upload one section at a time.

Creating a media item

After uploading media items to Google, you can create media items in Google Photos using upload tokens. An upload token is valid for one day after being created. A media item is always added to the user's library. Optionally, it can also be added to an album if your app has been granted permission.

Media items can be created only within the albums created by your app. For more information, see Authentication and authorization scopes.

To create new media items, make the following POST call:

POST https://photoslibrary.googleapis.com/v1/mediaItems:batchCreate
Content-type: application/json
Authorization: Bearer OAUTH2_TOKEN
REQUEST_BODY

The request body should specify a list of newMediaItems. Each newMediaItem contains an optional media description that is shown to the user. This description field is restricted to 1000 characters. It also contains an upload token that's specified inside a simpleMediaItem.

You can create a media item or multiple media items in a user’s library by specifying the descriptions and upload tokens:

{
  "newMediaItems": [
    {
      "description": "ITEM_DESCRIPTION",
      "simpleMediaItem": {
        "uploadToken": "UPLOAD_TOKEN"
      }
    }
   , ...
  ]
}

You can add media items to the library and to an album by specifying the album id. For more information, see Create albums.

{
  "albumId": "ALBUM_ID",
  "newMediaItems": [
    {
      "description": "ITEM_DESCRIPTION",
      "simpleMediaItem": {
        "uploadToken": "UPLOAD_TOKEN"
      }
    }
   , ...
  ]
}

You can also specify albumId and albumPosition to insert media items at a specific location in the album.

{
  "albumId": "ALBUM_ID",
  "newMediaItems": [
    {
      "description": "ITEM_DESCRIPTION",
      "simpleMediaItem": {
        "uploadToken": "UPLOAD_TOKEN"
      }
    }
    , ...
  ],
  "albumPosition": {
    "position": "AFTER_MEDIA_ITEM",
    "relativeMediaItemId": "MEDIA_ITEM_ID"
  }
}

For more details regarding positioning in albums, see Add enrichments.

Item creation response

Calls to library:batchCreate return a response that indicates the result of each of the media items that were to be created:

{
  "newMediaItemResult": [
    {
      "uploadToken": "UPLOAD_TOKEN",
      "status": {
        "code": "0"
      },
      "mediaItem": {
        "id": "MEDIA_ITEM_ID"
        "productUrl": "https://photos.google.com/photo/PHOTO_PATH",
        "description": "ITEM_DESCRIPTION"
        "baseUrl": "BASE_URL-DO_NOT_USE_DIRECTLY"
        "mediaMetadata": {
          "width": "MEDIA_WIDTH_IN_PX",
          "height": "MEDIA_HEIGHT_IN_PX"
          "creationTime": "CREATION_TIME",
          "photo": {},
        },
      }
    },
    {
      "uploadToken": "UPLOAD_TOKEN"
      "status": {
        "code": 13,
        "message": "Internal error"
      },
    }
  ]
}

The response consists of a list of newMediaItemResults that indicate the status and the uploadToken for the request. A non-zero status code indicates an error.

If the item was successfully added, a mediaItem is returned that contains its mediaItemId, productUrl and mediaMetadata. For more information, see Access media items.

If the media item is a video, it must be processed first. The mediaItem contains a status inside its mediaMetadata that describes the processing state of the video file. A newly uploaded file returns the PROCESSING status first, before it is READY for use. For details, see Access media items.

If you encounter an error during this call, follow the Best practices and retry your request with the uploadToken. You may want to keep track of successful additions, so the image can be inserted into the album at the correct position during the next request. For more information, see Create albums.

Results are always returned in the same order in which upload tokens were submitted.