Skip to main content

Package

@aws-sdk/client-s3

Installation

npm install @aws-sdk/client-s3

Creating the client

import { S3Client } from "@aws-sdk/client-s3";

const client = new S3Client({ region: "us-east-1" });
The client picks up credentials from the default credential provider chain (environment variables, ~/.aws/credentials, IAM role, etc.). Pass explicit credentials via the credentials option if needed.

Commands

import { S3Client, GetObjectCommand } from "@aws-sdk/client-s3";
import { Readable } from "stream";

const client = new S3Client({ region: "us-east-1" });

const response = await client.send(
  new GetObjectCommand({
    Bucket: "my-bucket",
    Key: "path/to/object.txt",
  })
);

// Convert the readable stream to a string
const body = await response.Body?.transformToString();
console.log(body);
response.Body is a SdkStream. Use transformToString() for text, transformToByteArray() for binary, or transformToWebStream() for a Web Streams ReadableStream.
import { S3Client, PutObjectCommand } from "@aws-sdk/client-s3";
import { createReadStream } from "fs";

const client = new S3Client({ region: "us-east-1" });

// Upload a string
await client.send(
  new PutObjectCommand({
    Bucket: "my-bucket",
    Key: "hello.txt",
    Body: "Hello, world!",
    ContentType: "text/plain",
  })
);

// Upload a Buffer
await client.send(
  new PutObjectCommand({
    Bucket: "my-bucket",
    Key: "data.bin",
    Body: Buffer.from("binary data"),
    ContentType: "application/octet-stream",
  })
);

// Upload a file stream
await client.send(
  new PutObjectCommand({
    Bucket: "my-bucket",
    Key: "photo.jpg",
    Body: createReadStream("/tmp/photo.jpg"),
    ContentType: "image/jpeg",
  })
);
For large files (>100 MB), use the Upload helper from @aws-sdk/lib-storage which handles multipart uploads automatically. See Multipart uploads.
import { S3Client, DeleteObjectCommand } from "@aws-sdk/client-s3";

const client = new S3Client({ region: "us-east-1" });

await client.send(
  new DeleteObjectCommand({
    Bucket: "my-bucket",
    Key: "path/to/object.txt",
  })
);
import { S3Client, ListObjectsV2Command } from "@aws-sdk/client-s3";

const client = new S3Client({ region: "us-east-1" });

const response = await client.send(
  new ListObjectsV2Command({
    Bucket: "my-bucket",
    Prefix: "images/",
    MaxKeys: 100,
  })
);

for (const object of response.Contents ?? []) {
  console.log(object.Key, object.Size, object.LastModified);
}

// Check if there are more pages
if (response.IsTruncated) {
  console.log("More results available, use ContinuationToken to paginate");
}
import { S3Client, CreateBucketCommand } from "@aws-sdk/client-s3";

const client = new S3Client({ region: "us-east-1" });

await client.send(
  new CreateBucketCommand({
    Bucket: "my-new-bucket",
    // Required for regions other than us-east-1
    // CreateBucketConfiguration: {
    //   LocationConstraint: "us-west-2",
    // },
  })
);
Bucket names are globally unique across all AWS accounts. Bucket creation in us-east-1 must omit CreateBucketConfiguration; all other regions require it.
import { S3Client, HeadObjectCommand } from "@aws-sdk/client-s3";

const client = new S3Client({ region: "us-east-1" });

const response = await client.send(
  new HeadObjectCommand({
    Bucket: "my-bucket",
    Key: "path/to/object.txt",
  })
);

console.log({
  contentLength: response.ContentLength,
  contentType: response.ContentType,
  lastModified: response.LastModified,
  etag: response.ETag,
  metadata: response.Metadata,
});
HeadObjectCommand returns metadata without downloading the object body. It throws NotFound (404) if the object does not exist.
import { S3Client, CopyObjectCommand } from "@aws-sdk/client-s3";

const client = new S3Client({ region: "us-east-1" });

await client.send(
  new CopyObjectCommand({
    Bucket: "destination-bucket",
    Key: "destination/path/object.txt",
    CopySource: "source-bucket/source/path/object.txt",
  })
);
CopySource must be URL-encoded if the source key contains special characters.

Pagination

Use paginateListObjectsV2 to iterate all pages without manually managing ContinuationToken:
import { S3Client, paginateListObjectsV2 } from "@aws-sdk/client-s3";

const client = new S3Client({ region: "us-east-1" });

const paginator = paginateListObjectsV2(
  { client },
  {
    Bucket: "my-bucket",
    Prefix: "logs/",
  }
);

for await (const page of paginator) {
  for (const object of page.Contents ?? []) {
    console.log(object.Key);
  }
}

Presigned URLs

Generate time-limited URLs for unauthenticated upload and download.

Multipart uploads

Upload large files efficiently with @aws-sdk/lib-storage.

CRT dependency for Multi-Region Access Points

Some S3 features, including Multi-Region Access Points and S3 Object Integrity CRC checksums, require the AWS Common Runtime (CRT). Install the optional dependency to enable them:
npm install @aws-sdk/signature-v4-crt
Then import it once at the top of your application entry point. No API calls are needed — the package registers itself automatically:
// CommonJS
require("@aws-sdk/signature-v4-crt");

// ESM / TypeScript
import "@aws-sdk/signature-v4-crt";

Build docs developers (and LLMs) love