status 501 and statusText Not Implemented on uploading video file to AWS S3 using pre signed url using node js fetch

huangapple go评论71阅读模式
英文:

status 501 and statusText Not Implemented on uploading video file to AWS S3 using pre signed url using node js fetch

问题

I want to upload video file to S3 using pre signed url. But I am getting status: 501, statusText: 'Not Implemented'.

I tried to get help from other similar question on stackovderflow and tried setting content type and content length but still getting same error.

Here is code by which I generated pre signed url

var S3 = require('aws-sdk/clients/s3')

async function getS3UploadSignedUrl() {
    var s3 = new S3({
        accessKeyId: config.aws.accessKeyId,
        secretAccessKey: config.aws.secretAccessKey,
        region: config.aws.region,
        apiVersion: '2010-12-01'
    });
    
    let params = {
        Bucket: config.aws.s3Bucket,
        Key: 'myVideo.mp4',
        Expires: 60 * 60, // in seconds
        ContentType: 'video/mp4',
        ACL: 'public-read',
    }
    let signedUrl = await s3.getSignedUrl('putObject', params);
    console.log('signedUrl', signedUrl)
}

I am trying to upload using this code

const fs = require('fs');

const FILE_PATH = '/home/alok/Downloads/video.mp4';
const signedUrl = 'https://my pre signed url';

const fileStream = fs.createReadStream(FILE_PATH);
const contentLength = fs.statSync(FILE_PATH).size;

async function uploader() {
    var options = {
        method: "PUT",
        headers: { "content-type": "video/mp4" },
        body: fileStream,
        'Content-Length': contentLength
    }
    let response = await fetch(signedUrl, options)
    console.log(response)
}

uploader()

My bucket Bucket policy

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "PublicRead",
            "Effect": "Allow",
            "Principal": "*",
            "Action": [
                "s3:GetObject",
                "s3:GetObjectVersion",
                "s3:PutObject",
                "s3:PutObjectAcl"
            ],
            "Resource": "arn:aws:s3:::my-bucket/*"
        }
    ]
}

My Cross-origin resource sharing (CORS) details

[
    {
        "AllowedHeaders": [
            "*"
        ],
        "AllowedMethods": [
            "GET",
            "HEAD",
            "PUT",
            "POST"
        ],
        "AllowedOrigins": [
            "*"
        ],
        "ExposeHeaders": [
            "x-amz-server-side-encryption",
            "x-amz-request-id",
            "x-amz-id-2"
        ],
        "MaxAgeSeconds": 3000
    }
]

What I am missing so not able to uplad video?

英文:

I want to upload video file to S3 using pre signed url. But I am getting
status: 501, statusText: 'Not Implemented'.

I tried to get help from other similar question on stackovderflow and tried setting content type and content length but still getting same error.

Here is code by which I generated pre signed url

var S3 = require('aws-sdk/clients/s3')

async function getS3UploadSignedUrl() {
    var s3 = new S3({
        accessKeyId: config.aws.accessKeyId,
        secretAccessKey: config.aws.secretAccessKey,
        region: config.aws.region,
        apiVersion: '2010-12-01'
    });
    
    let params = {
        Bucket: config.aws.s3Bucket,
        Key: 'myVideo.mp4',
        Expires: 60 * 60, // in seconds
        ContentType: 'video/mp4',
        ACL: 'public-read',
    }
    let signedUrl = await s3.getSignedUrl('putObject', params);
    console.log('signedUrl', signedUrl)
}

I am trying to upload using this code

const fs = require('fs');

const FILE_PATH = '/home/alok/Downloads/video.mp4';
const signedUrl = 'https://my pre signed url'

const fileStream = fs.createReadStream(FILE_PATH);
const contentLength = fs.statSync(FILE_PATH).size;

async function uploader() {
    var options = {
        method: "PUT",
        headers: { "content-type": "video/mp4" },
        body: fileStream,
        'Content-Length': contentLength
    }
    let response = await fetch(signedUrl, options)
    console.log(response)
}

uploader()

My bucket Bucket policy

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Sid": "PublicRead",
            "Effect": "Allow",
            "Principal": "*",
            "Action": [
                "s3:GetObject",
                "s3:GetObjectVersion",
                "s3:PutObject",
                "s3:PutObjectAcl"
            ],
            "Resource": "arn:aws:s3:::my-bucket/*"
        }
    ]
}

My Cross-origin resource sharing (CORS) details

[
    {
        "AllowedHeaders": [
            "*"
        ],
        "AllowedMethods": [
            "GET",
            "HEAD",
            "PUT",
            "POST"
        ],
        "AllowedOrigins": [
            "*"
        ],
        "ExposeHeaders": [
            "x-amz-server-side-encryption",
            "x-amz-request-id",
            "x-amz-id-2"
        ],
        "MaxAgeSeconds": 3000
    }
]

What I am missing so not able to uplad video?

答案1

得分: 1

fetch 可能需要一些额外的配置来上传文件。使用 axios 可以正常工作。

const axios = require('axios');
const fs = require('fs');

const fileContent = fs.readFileSync('/home/alok/Downloads/video.mp4');

let signedUrl = 'https://我的预签名URL';

axios.put(signedUrl, fileContent, {
    headers: {
        'Content-Type': 'video/mp4'
    }
})
    .then(response => {
        console.log('文件上传成功!', response.data);
    })
    .catch(error => {
        console.error('上传文件出错:', error);
    });

英文:

fetch might require some extra configuration for uploading file. Its working file with axios

const axios = require('axios');
const fs = require('fs');

const fileContent = fs.readFileSync('/home/alok/Downloads/video.mp4');

let signedUrl = 'https://my pre signed url'

axios.put(signedUrl, fileContent, {
    headers: {
        'Content-Type': 'video/mp4'
    }
})
    .then(response => {
        console.log('File uploaded successfully!', response.data);
    })
    .catch(error => {
        console.error('Error uploading file:', error);
    });

答案2

得分: 0

Browser fetch is working fine

<html>

<body>
    <script>
        let url = "https://我的预签名URL";

        async function handleForm(event) {
            event.preventDefault();
            const form = event.target;
            const formData = new FormData(form);
            const file = formData.get("myFile");
            console.log("我的文件", file);

            let options = {
                method: "PUT",
                headers: { 'Content-Type': 'video/mp4' },
                body: file
            };
            let response = await fetch(url, options);
            console.log('响应', response)
        }
    </script>

    <form onSubmit="handleForm(event)">
        <input type="file" id="myFile" name="myFile" />
        <input type="submit" />
    </form>

</body>

</html>
英文:

Browser fetch is working fine

<html>

<body>
    <script>
        let url = "https://my pre signed url";

        async function handleForm(event) {
            event.preventDefault();
            const form = event.target;
            const formData = new FormData(form);
            const file = formData.get("myFile");
            console.log("my file", file);

            let options = {
                method: "PUT",
                headers: { 'Content-Type': 'video/mp4' },
                body: file
            };
            let response = await fetch(url, options);
            console.log('response', response)
        }
    </script>

    <form onSubmit="handleForm(event)">
        <input type="file" id="myFile" name="myFile" />
        <input type="submit" />
    </form>

</body>

</html>

huangapple
  • 本文由 发表于 2023年4月13日 18:29:44
  • 转载请务必保留本文链接:https://go.coder-hub.com/76004381.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定