---
title: "S3"
description: "How to access S3 API, how to authenticate, which Amazon S3 API features are compatible with S3 API, and how to work with AWS SDK"
---

import { CustomTable } from '@selectel/docux/components';

:::warning

If you use S3 settings configured before the storage update on 09/29/2023, update them by 09/15/2026. For more details, see the [Configuring S3 after update](/s3/manage/configure-storage-update/) article.

After 09/15/2026, old settings (users, URLs, etc.) will stop working.

:::

## Getting started \{#getting-started}

S3 API is an API based on the Amazon S3 API, designed for working with S3 resources. With S3 API, you can:

* view information about the number and size of buckets and objects within an account;
* create and remove buckets;
* upload, view, copy, move, download, and remove objects in buckets;
* manage multipart object uploads;
* manage CORS, etc.

### Accessing the API \{#access-to-api}

Only authorized access to the S3 API is possible.

Для доступа к бакету через S3 API у пользователя должна быть роль with доступом к S3, подробнее in инструкции [Управлять доступом к S3](/s3/about/manage-access/)

The address (URL) for Path-Style addressing (default) can be found in the [list of URLs](/api/urls/).

If Virtual Hosted addressing is enabled, you can access the bucket via the address `<bucket_name>.<s3_domain>`.

### Authentication \{#authentication}

Authentication in S3 API is performed using request signing. We support AWS Signature Version 4 and AWS Signature Version 2.

Generating a signature requires access keys, which can be obtained when [issuing an S3 key to a user](/access-control/manage/edit-user-data-or-role/#issue-s3-key):

* Access Key ID — value of the **Access key** field from an S3 key;
* Secret Access Key — value of the **Secret key** field from an S3 key.

A request can be signed using one of the following methods:

* via the Authorization HTTP header. For more details, see [Authenticating Requests: Using the Authorization Header (AWS Signature Version 4](https://docs.aws.amazon.com/AmazonS3/latest/API/sigv4-auth-using-authorization-header.html)) in the Amazon documentation;
* using query parameters or a pre-signed URL (Presigned URL). Using this method, you can specify all request parameters in the URL. For more details, see [Authenticating Requests: Using Query Parameters (AWS Signature Version 4](https://docs.aws.amazon.com/AmazonS3/latest/API/sigv4-query-string-auth.html)) in the Amazon documentation.

The request signature expiration time is 15 minutes.

## Compatibility \{#compatibility}

S3 API is compatible with the following Amazon S3 API features:

<CustomTable>
  <table>
    <thead>
      <tr>
        <th>Method</th><th>Compatibility</th>
      </tr>
    </thead>

    <tbody>
      <tr>
        <td>Bucket CRUD</td><td>✓</td>
      </tr>

      <tr>
        <td>Bucket Acl</td><td>✗</td>
      </tr>

      <tr>
        <td>Bucket CORS</td><td>✓</td>
      </tr>

      <tr>
        <td>Bucket Encryption</td><td>✗<br />Client-side encryption (AWS SDK) is supported</td>
      </tr>

      <tr>
        <td>Bucket Lifecycle</td><td>✗</td>
      </tr>

      <tr>
        <td>Bucket Location</td><td>✓</td>
      </tr>

      <tr>
        <td>Bucket Logging</td><td>✗</td>
      </tr>

      <tr>
        <td>Bucket Metrics Configuration</td><td>✗</td>
      </tr>

      <tr>
        <td>Bucket Notification</td><td>✗</td>
      </tr>

      <tr>
        <td>Bucket Ownership Controls</td><td>✗</td>
      </tr>

      <tr>
        <td>Bucket Policy</td><td>✓</td>
      </tr>

      <tr>
        <td>Bucket Replication</td><td>✗</td>
      </tr>

      <tr>
        <td>Bucket Request Payment</td><td>✗</td>
      </tr>

      <tr>
        <td>Bucket Tagging</td><td>✗</td>
      </tr>

      <tr>
        <td>Bucket Versioning</td><td>✓</td>
      </tr>

      <tr>
        <td>Bucket Website</td><td>✗</td>
      </tr>

      <tr>
        <td>Conditional Writes</td><td>✓</td>
      </tr>

      <tr>
        <td>Object CRUD</td><td>✓</td>
      </tr>

      <tr>
        <td>Object Copy</td><td>✓</td>
      </tr>

      <tr>
        <td>Object Acl</td><td>✗<br />Get ACL works</td>
      </tr>

      <tr>
        <td>Object Content</td><td>✗</td>
      </tr>

      <tr>
        <td>Object Lock Configuration</td><td>✓</td>
      </tr>

      <tr>
        <td>Object Response</td><td>✗</td>
      </tr>

      <tr>
        <td>Object Retention</td><td>✗</td>
      </tr>

      <tr>
        <td>Object Tagging</td><td>✗</td>
      </tr>

      <tr>
        <td>Object Torrent</td><td>✗</td>
      </tr>

      <tr>
        <td>Object Versions</td><td>✓</td>
      </tr>

      <tr>
        <td>Multipart Upload</td><td>✓</td>
      </tr>

      <tr>
        <td>Public Access Block</td><td>✗<br />All requests are Private by default</td>
      </tr>
    </tbody>
  </table>
</CustomTable>

## AWS SDK \{#aws-sdk}

### Python \{#python}

#### Boto \{#boto}

[boto3](https://github.com/boto/boto3) are software development kits (SDK) for Python 3.x programming languages. The SDKs are designed to work with AWS services.

1. Install boto. For more details, see the [boto3](https://github.com/boto/boto3/blob/develop/README.rst#quick-start) documentation.
2. In your home directory, create the `~/.aws/credentials` configuration file:

```
[default]
    aws_access_key_id = <access_key>
    aws_secret_access_key = <secret_key>
```

Specify:

* `<access_key>` — значение поля **Access key** из [S3-ключа](/access-control/manage/edit-user-data-or-role/#issue-s3-key);
* `<secret_key>` — value of the **Secret key** field from an S3 key.

3. In your home directory, create the `~/.aws/config` configuration file:

```
[default]
    region=<pool>
```

#### Operation examples \{#boto-operations-examples}

```
#!/usr/bin/env python
#-*- coding: utf-8 -*-
import boto3

# Authorization
s3 = boto3.client(
   service_name='s3',
   endpoint_url='<url>'
)

# Upload object from string
s3.put_object(Bucket="BucketName", Key="ObjectName1", Body="Test")

# Upload object from file
s3.upload_file("data.docx", "BucketName", "ObjectName2")

# Get list of objects in the bucket
for key in s3.list_objects(Bucket="BucketName")["Contents"]:
   print(key["Key"])

# Download object
get_object_response = s3.get_object(Bucket="BucketName", Key="ObjectName2")
print(get_object_response["Body"].read())

# Delete multiple objects
objects_to_delete = [{"Key": "ObjectName1"}, {"Key": "ObjectName2"}]
s3.delete_objects(Bucket="BucketName", Delete={"Objects": objects_to_delete})
```

#### Example for boto3 \{#boto-example}

Create an S3 client by providing an endpoint\_url, pool, and S3 key (EC2 key) [issued to the user](/access-control/manage/edit-user-data-or-role/#issue-s3-key):

```
s3 = boto3.client("s3", endpoint_url="<url>", region_name="<pool>", aws_access_key_id="access_key", aws_secret_access_key="secret_key")
```

Call the `generate_presigned_post()` method by passing the name of the bucket to which the upload will be performed, and the key name, which may contain the `${filename}` pattern for the file name provided by the user at the moment of uploading. This call will return a dictionary with the URL to which the form should be sent, as well as a `fields` dictionary containing all necessary filled fields for this form (X-Amz-Algorithm, X-Amz-Credential, X-Amz-Date, X-Amz-Signature, Policy).

```
post = s3.generate_presigned_post(bucket, key)
```

If you need to add additional fields to an object (and form), for example, the Content-Type header, pass a dictionary with these fields as the Fields argument. Also, according to the [Policy specification](https://docs.aws.amazon.com/AmazonS3/latest/API/sigv4-HTTPPOSTConstructPolicy.html), you need to describe each additional field in the `conditions` array (the `Conditions` argument in boto).

```
post = s3.generate_presigned_post(bucket, key,
                                  Fields={"Content-Type": "image/webp"},
                                  Conditions=[["eq", "$content-type", "image/webp"]])
```

From the data obtained, you can create an HTML form or reproduce the request via requests:

```
requests.post(post["url"], data=post["fields"], files=[("file", ("filename", b"body_data"))])
```

When generating an HTML form, note that the file field with the uploaded file data must be at the end of the form.

### PHP \{#php}

[AWS SDK for PHP](https://aws.amazon.com/ru/sdk-for-php/) is a software development kit for working with AWS services.

The SDK is a modern open-source PHP library that simplifies the integration of a PHP application with S3.

To connect the library using the Composer dependency management tool, follow these steps:

1. Install Composer:

```
curl -sS 'https://getcomposer.org/installer' | php
```

2. Run the Composer command to install the latest stable version of the SDK:

```
php composer.phar require aws/aws-sdk-php
```

3. Include aws-sdk-php in your script. Authorization requires the **Access Key** and **Secret Key** values from the [S3 key](/access-control/manage/edit-user-data-or-role/#issue-s3-key).

#### Operation examples \{#php-operations-examples}

```
<?php
require "vendor/autoload.php";

use Aws\S3\S3Client;
// Create client
$s3Client = new S3Client([
   "version" 	=> "latest",
   "region"  	=> "<pool>",
   "use_path_style_endpoint" => true,
   "credentials" => [
   	"key"	=> "<access_key>",
   	"secret" => "<secret_key>",
   ],
   "endpoint" => "<url>"
]);

// Upload object
$s3Client->putObject([
   "Bucket" => "BucketName",
   "Key"	=> "ObjectName",
   "Body"   => "Test"
]);

// Download object
$result = $s3Client->getObject([
   "Bucket" => "BucketName",
   "Key"	=> "ObjectName"
]);

echo $result["Body"];
```

Specify:

* `<access_key>` — значение поля **Access key** из [S3-ключа](/access-control/manage/edit-user-data-or-role/#issue-s3-key);
* `<secret_key>` — value of the **Secret key** field from an S3 key.

### JavaScript \{#javascript}

[AWS SDK for Node.js](https://aws.amazon.com/ru/sdk-for-node-js/) is a software development kit for using JavaScript with AWS services in the Node.js environment.

#### Example for Node.js \{#javascript-node-js-example}

```
import {
  S3Client,
  PutObjectCommand,
  CreateBucketCommand,
  DeleteObjectCommand,
  DeleteBucketCommand,
  paginateListObjectsV2,
  GetObjectCommand,
} from "@aws-sdk/client-s3";
import { createInterface } from "node:readline/promises";

export async function main() {
  const s3 = new S3Client({
    region: "<region>",
    endpoint: "<endpoint>",
    apiVersion: "latest",
    credentials: {
      accessKeyId: "<access-key>",
      secretAccessKey: "<secret-key>",
    },
  });

  const bucketName = `test-bucket-${Date.now()}`;
  const fileName = "test-file.txt";

  //Create S3 bucket
  await s3.send(
    new CreateBucketCommand({
      Bucket: bucketName,
    })
  );

  //Put an object into an S3 bucket.
  await s3.send(
    new PutObjectCommand({
      Bucket: bucketName,
      Key: fileName,
      Body: "Hello JavaScript SDK!",
    })
  );

  //Get object
  const { Body } = await s3.send(
    new GetObjectCommand({
      Bucket: bucketName,
      Key: fileName,
    })
  );
  console.log(await Body.transformToString());
}

// Confirm resource deletion.
const prompt = createInterface({
  input: process.stdin,
  output: process.stdout,
});

const result = await prompt.question("Empty and delete bucket? (y/n) ");
prompt.close();

if (result === "y") {
  // Create an async iterator over lists of objects in a bucket.
  const paginator = paginateListObjectsV2(
    { client: s3 },
    { Bucket: bucketName }
  );
  for await (const page of paginator) {
    const objects = page.Contents;
    if (objects) {
      // For every object in each page, delete it.
      for (const object of objects) {
        await s3.send(
          new DeleteObjectCommand({ Bucket: bucketName, Key: object.Key })
        );
      }
    }
  }

  // Once all the objects are gone, the bucket can be deleted.
  await s3.send(new DeleteBucketCommand({ Bucket: bucketName }));
}

main();
```

Specify:

* `<access_key>` — значение поля **Access key** из [S3-ключа](/access-control/manage/edit-user-data-or-role/#issue-s3-key);
* `<secret_key>` — value of the **Secret key** field from an S3 key;
* `<url>` — [S3 API domain](/s3/manage/domains/#s3-api-domains), depends on the [pool](/infrastructure/locations/#pool) where S3 is located;
* `<pool>` —  [пул](/infrastructure/locations/#pool), in котором находится S3.

### Java \{#java}

```
// Configure S3 client connection
AWSCredentials credentials = new BasicAWSCredentials(
        "<access_key>",
        "<secret_key>"
);

EndpointConfiguration endpoint =
        new EndpointConfiguration("<url>", "<pool>");

AmazonS3 s3client = AmazonS3ClientBuilder
        .standard()
        .withCredentials(new AWSStaticCredentialsProvider(credentials))
        .withPathStyleAccessEnabled(true)
        .withEndpointConfiguration(endpoint)
        .build();

// Create bucket
String bucketName = "s3bucket";
String objectName = "s3object";

if(!s3client.doesBucketExistV2(bucketName)) {
        s3client.createBucket(bucketName);
}

// Upload object
s3client.putObject(
        bucketName,
        objectName,
        "sample-data"
);

// Download object
S3Object s3object = s3client.getObject(bucketName, objectName);
S3ObjectInputStream inputStream = s3object.getObjectContent();

inputStream.transferTo(new FileOutputStream("downloaded-object"));

// Delete object
s3client.deleteObject(bucketName, objectName);

// Delete bucket
s3client.deleteBucket(bucketName);
```

Specify:

* `<access_key>` — значение поля **Access key** из [S3-ключа](/access-control/manage/edit-user-data-or-role/#issue-s3-key);
* `<secret_key` — значение поля **Secret key** из S3-ключа.
