将视频上传到.net中的AWS S3

时间:2020-06-30 16:58:12

标签: amazon-web-services asp.net-core amazon-s3 .net-core

因此,我正在尝试将视频上传到我的S3存储桶中,代码几乎可以正常工作,它当前所做的是将一个空文件上传到存储桶中,因此API可以与AWS正确交互,但未在请求中发送视频。当我发送图像(并将“ .mp4”更改为“ .png”)时,它可以正常运行,但是当我上传视频时,它不起作用

控制器

    [HttpPost("{userId}/video")]
    [RequestSizeLimit(999_000_000)]
    public async Task<ActionResult> VideoUpload(int userId, [FromForm] PhotoForCreationDto photoForCreationDto)
    {
       AmazonS3VideoUploader amazonS3v = new AmazonS3VideoUploader();

        var keyName = photoForCreationDto.Username + getKeyName() + ".mp4";

        var file = photoForCreationDto.File;

        amazonS3v.UploadFile(file, keyName);

        return Ok();
    }

存储库

    public async void UploadFile(IFormFile file, string keyName)
    {
        var client = new AmazonS3Client(myAwsAccesskey, myAwsSecret, Amazon.RegionEndpoint.EUWest2);

        using (var stream = file.OpenReadStream())
        {
            try
            {
                PutObjectRequest putRequest = new PutObjectRequest
                {
                    BucketName = bucketName,
                    Key = keyName,
                    InputStream = stream,
                    // ContentType = "image/png"
                    ContentType = "video/mp4"
                };

                PutObjectResponse response = await client.PutObjectAsync(putRequest);

            }
            catch (AmazonS3Exception amazonS3Exception)
            {
                if (amazonS3Exception.ErrorCode != null &&
                    (amazonS3Exception.ErrorCode.Equals("InvalidAccessKeyId")
                    ||
                    amazonS3Exception.ErrorCode.Equals("InvalidSecurity")))
                {
                    throw new Exception("Check the provided AWS Credentials.");
                }
                else
                {
                    throw new Exception("Error occurred: " + amazonS3Exception.Message);
                }
            }
        }

    }
}

过一会儿我出现这个错误:

Unhandled Exception: System.ObjectDisposedException: Cannot access a closed file.
   at System.IO.FileStream.get_Position()
   at Microsoft.AspNetCore.WebUtilities.FileBufferingReadStream.get_Position()
   at Microsoft.AspNetCore.Http.Internal.ReferenceReadStream.VerifyPosition()
   at Microsoft.AspNetCore.Http.Internal.ReferenceReadStream.set_Position(Int64 value)
   at Amazon.Runtime.Internal.RetryHandler.InvokeAsync[T](IExecutionContext executionContext) in D:\JenkinsWorkspaces\trebuchet-stage-release\AWSDotNetPublic\sdk\src\Core\Amazon.Runtime\Pipeline\RetryHandler\RetryHandler.cs:line 149
   at Amazon.Runtime.Internal.CallbackHandler.InvokeAsync[T](IExecutionContext executionContext)
   at Amazon.Runtime.Internal.CallbackHandler.InvokeAsync[T](IExecutionContext executionContext)
   at Amazon.S3.Internal.AmazonS3ExceptionHandler.InvokeAsync[T](IExecutionContext executionContext)
   at Amazon.Runtime.Internal.ErrorCallbackHandler.InvokeAsync[T](IExecutionContext executionContext)
   at Amazon.Runtime.Internal.MetricsHandler.InvokeAsync[T](IExecutionContext executionContext)
   at cartalk.api.Data.AmazonS3VideoUploader.UploadFile(IFormFile file, String keyName) in D:\Projects in progress\Car talk\_application - current\cartalk.api\Data\AmazonS3VideoUploader.cs:line 82
   at System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext, ContextCallback callback, Object state)
--- End of stack trace from previous location where exception was thrown ---
   at System.Threading.ThreadPoolWorkQueue.Dispatch()

1 个答案:

答案 0 :(得分:0)

要解决此错误,我不得不稍微更改一下代码,而不是将视频(System.IO.Stream)发送到存储库,而是必须在控制器本身内部进行所有操作。我认为发生这种情况的原因是因为在请求发送到AWS之前流已关闭。在此处了解更多信息:System.ObjectDisposedException: Cannot access a closed Stream

这就是我将其更改为:

[HttpPost("{userId}/video")]
[RequestSizeLimit(999_000_000)]
public async Task<ActionResult> VideoUpload(int userId, [FromForm] PhotoForCreationDto photoForCreationDto)
        {

        AmazonS3VideoUploader amazonS3v = new AmazonS3VideoUploader();

        var keyName = getKeyName() + ".mp4";

        var file = photoForCreationDto.File;

        var client = new AmazonS3Client(myAwsAccesskey, myAwsSecret, Amazon.RegionEndpoint.EUWest2);

        if (file.Length > 0)
        {
            using (var stream = file.OpenReadStream())
            {
                try
                {
                    PutObjectRequest putRequest = new PutObjectRequest
                    {
                        BucketName = bucketName,
                        Key = keyName,
                        InputStream = stream,
                        ContentType = "video/mp4"
                    };

                    await client.PutObjectAsync(putRequest);

                }
                catch (AmazonS3Exception amazonS3Exception)
                {
                    if (amazonS3Exception.ErrorCode != null &&
                        (amazonS3Exception.ErrorCode.Equals("InvalidAccessKeyId")
                        ||
                        amazonS3Exception.ErrorCode.Equals("InvalidSecurity")))
                    {
                        throw new Exception("Check the provided AWS Credentials.");
                    }
                    else
                    {
                        throw new Exception("Error occurred: " + amazonS3Exception.Message);
                    }
                }

            }
        }
        return Ok();
    }