Knoten AWS SDK S3 Vordefinierte URL generieren

111

Ich verwende das NodeJS AWS SDK, um eine vorgegebene S3-URL zu generieren. Die Dokumente geben ein Beispiel für das Generieren einer vorgegebenen URL .

Hier ist mein genauer Code (ohne vertrauliche Informationen):

const AWS = require('aws-sdk')

const s3 = new AWS.S3()
AWS.config.update({accessKeyId: 'id-omitted', secretAccessKey: 'key-omitted'})

// Tried with and without this. Since s3 is not region-specific, I don't
// think it should be necessary.
// AWS.config.update({region: 'us-west-2'})

const myBucket = 'bucket-name'
const myKey = 'file-name.pdf'
const signedUrlExpireSeconds = 60 * 5

const url = s3.getSignedUrl('getObject', {
    Bucket: myBucket,
    Key: myKey,
    Expires: signedUrlExpireSeconds
})

console.log(url)

Die URL, die generiert wird, sieht folgendermaßen aus:

https://bucket-name.s3-us-west-2.amazonaws.com/file-name.pdf?AWSAccessKeyId=[access-key-omitted]&Expires=1470666057&Signature=[signature-omitted]

Ich kopiere diese URL in meinen Browser und erhalte die folgende Antwort:

<Error>
  <Code>NoSuchBucket</Code>
  <Message>The specified bucket does not exist</Message>
  <BucketName>[bucket-name-omitted]</BucketName>
  <RequestId>D1A358D276305A5C</RequestId>
  <HostId>
    bz2OxmZcEM2173kXEDbKIZrlX508qSv+CVydHz3w6FFPFwC0CtaCa/TqDQYDmHQdI1oMlc07wWk=
  </HostId>
</Error>

Ich weiß, dass der Eimer existiert. Wenn ich über die AWS-Web-GUI zu diesem Element navigiere und darauf doppelklicke, wird das Objekt mit der URL geöffnet und funktioniert einwandfrei:

https://s3-us-west-2.amazonaws.com/[bucket-name-omitted]/[file-name-omitted].pdf?X-Amz-Date=20160808T141832Z&X-Amz-Expires=300&X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Signature=[signature-omitted]&X-Amz-Credential=ASIAJKXDBR5CW3XXF5VQ/20160808/us-west-2/s3/aws4_request&X-Amz-SignedHeaders=Host&x-amz-security-token=[really-long-key]

Daher muss ich glauben, dass ich mit der Verwendung des SDK etwas falsch machen muss.

Dustin
quelle
1
Untersuchen Sie Ihre generierte URL sorgfältig. NoSuchBucketbedeutet, dass der https://>>>here<<<.s3-us-west-2.amazonaws.comin der URL angezeigte Bucket-Name nicht vorhanden ist. Nichts in Ihrem Signaturprozess, Ihrer Richtlinie, Ihren Berechtigungen, Ihrem Schlüssel oder Ihrem Geheimnis kann diesen bestimmten Fehler erzeugen.
Michael - sqlbot
8
Der Link zum Dokumentbeispiel wurde nach docs.aws.amazon.com/AWSJavaScriptSDK/latest/AWS/… verschoben
Joël
@Dustin, wie sicher es ist, wenn der ACCESS-Schlüssel in der URL angezeigt wird und sich die URL bei jedem Funktionsaufruf
ändert
Es ist nicht sicher, den secretAccessKey an einem öffentlichen Ort wie der URL zu platzieren, und ja, ich glaube, die URL ändert sich jedes Mal. @ Kailashyogeshwar
Dustin
5
Für diejenigen, die hierher kommen wie ich und nicht die genaue Antwort bekommen haben, ist dies das, was ich brauchte. In jeder der oben genannten URLs wird eine andere Signaturversion verwendet. Legen Sie die Signaturversion fest, bevor Sie die S3-Instanz erstellen, oder legen Sie sie in der S3-Konfiguration fest. new AWS.S3({ signatureVersion: 'v4' })erzwingt die Signatur Version 4. Dies war eine Voraussetzung für mich mit einem SSE KMS-verschlüsselten Objekt.
Eric E.

Antworten:

97

Dustin,

Ihr Code ist korrekt. Überprüfen Sie Folgendes:

  1. Ihre Bucket-Zugriffsrichtlinie.

  2. Ihre Bucket-Berechtigung über Ihren API-Schlüssel.

  3. Ihr API-Schlüssel und Ihr Geheimnis.

  4. Ihr Eimername und Schlüssel.

Reza Mousavi
quelle
91
Peinlicherweise hatte ich einen Tippfehler in meinem Eimernamen.
Dustin
36
Klassisch. Passiert den Besten von uns.
Vlad A. Ionescu
2

Ich hatte einen Anwendungsfall, in dem node.js verwendet wurde. Ich wollte ein Objekt von s3 abrufen und es an einen temporären Ort herunterladen und es dann als Anhang zum Drittanbieter-Service geben! So habe ich den Code gebrochen:

  1. Holen Sie sich signierte URL von S3
  2. Machen Sie einen Restaufruf, um das Objekt zu erhalten
  3. Schreiben Sie das in den lokalen Ort

Es kann jedem helfen; wenn es den gleichen Anwendungsfall gibt; chekout unter link ; https://medium.com/@prateekgawarle183/fetch-file-from-aws-s3-using-pre-signed-url-and-store-it-into-local-system-879194bfdcf4

Prateek G.
quelle
-1

Versuchen Sie diese Funktion mit Versprechen.

const AWS = require("aws-sdk");
const s3 = new AWS.S3({
  accessKeyId: 'AK--------------6U',
  secretAccessKey: 'kz---------------------------oGp',
  Bucket: 'bucket-name'
});

const getSingedUrl = async () => {    
  const params = {
    Bucket: 'bucket_name',
    Key: 'file-name.pdf',
    Expires: 60 * 5
  };

  try {
    const url = await new Promise((resolve, reject) => {
      s3.getSignedUrl('getObject', params, (err, url) => {
        err ? reject(err) : resolve(url);
      });
    });
    console.log(url)
  } catch (err) {
    if (err) {
      console.log(err)
    }
  }
}


getSingedUrl()
Ankit Kumar Rajpoot
quelle