S3 presigned post url problem


I’m unable to get S3 presigned post to work with localstack.
I’m using @aws-sdk/client-s3 and @aws-sdk/s3-presigned-post npm packages on a node application to communicate with S3.
My S3 client config:

  endpoint: http://localhost:4566,
  forcePathStyle: true,

Looks like the issue is that the url returned by @aws-sdk/s3-presigned-post createPresignedPost is http://localhost:4566/ without bucket name appended to it (source).
I’m not sure how this is supposed to work with localstack, but it doesn’t seem to handle presigned post calls to base path and when I manually append the bucket name to the url, it is working as expected.

Is this a bug in the @aws-sdk/s3-presigned-post createPresignedPost and it should respect forcePathStyle config or should localstack handle the post calls to base path?


Hi and thanks for your report.

I’ve tried to reproduce your issue, and with a sample I’ll attach, and the url returned contains the bucket in the path.
I used the sample data provided in @aws-sdk/s3-presigned-post | AWS SDK for JavaScript v3

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

const client = new S3Client({
  region: "us-east-1",
  forcePathStyle: true,
  endpoint: "http://localhost:4566"

const Conditions = [{ acl: "public-read" }, { bucket: "bucketname" }, ["starts-with", "$key", "user/eric/"]];
const Bucket = "bucketname";
const Key = "user/eric/1";
const Fields = {
  acl: "public-read",
const { url, fields } = await createPresignedPost(client, {
  Expires: 600, //Seconds before the presigned post expires. 3600 by default.
// -> http://localhost:4566/bucketname
// {
//   acl: 'public-read',
//   bucket: 'bucketname',
//   'X-Amz-Algorithm': 'AWS4-HMAC-SHA256',
//   'X-Amz-Credential': 'test/20230206/us-east-1/s3/aws4_request',
//   'X-Amz-Date': '20230206T124506Z',
//   key: 'user/eric/1',
//   Policy: '<base64-data-policy>',
//   'X-Amz-Signature': '<signature>'
// }

In any case, LocalStack won’t be able to handle a POST call to the base path.
If the sample above does not help you, would you mind sharing a sample to reproduce the issue?

Hi @bentsku and thanks for your response.

Interesting. I tested it now and it indeed is working as expected.
I was so sure that it was not working before that I decided to do a sanity check.
I do not remember exactly which version I was initially using, but I picked a random one release 2 weeks ago and it seems that AWS has fixed something as it is working as expected with v3.266.0 (current latest), but not with v3.258.0.

I checked again the source and looks like they have fixed it 5 days ago :slight_smile: .

Hi @arturv! Oh, that’s very interesting.

It is always a bit hard to debug between all SDK available (as our integration test suite mostly uses boto), and we didn’t hear about this issue yet, but I’m really glad it got fixed now.

And thank you for your feedback, at least we know there’s a potential issue there if this problem comes up again!