Spandana Krishnan
Spandana Krishnan

Reputation: 323

How to upload an image directly to S3, without letting java webapp running in Ec2 to store the Multipart image?

In my laptop, localhost,

Following code uploads image uploaded via browser, and then it uploads to S3.

I came to know that Elastic Beanstalk applications run on Amazon EC2 instances that have no persistent local storage. We should write the file directly to S3.

How to write file directly to S3, when my java webapp runs in Ec2 instances?

This is the code I use to upload image to S3 which works fine in my localhost

try {
            final ObjectMetadata objectMetadata = new ObjectMetadata();
            objectMetadata.setContentType(file.getContentType());
            byte[] contentBytes = null;
            try {
              final InputStream is = file.getInputStream();
              contentBytes = IOUtils.toByteArray(is);
            } catch (final IOException e) {
              log.error("Failed while reading bytes from %s" + e.getMessage());
            }

            final Long contentLength = Long.valueOf(contentBytes.length);
            objectMetadata.setContentLength(contentLength);
            objectMetadata.setHeader("filename", fileNameWithExtn);

            /*
             * Reobtain the tmp uploaded file as input stream
             */
            final InputStream inputStream = file.getInputStream();

            final File convFile = new File(fileNameWithExtn);
            file.transferTo(convFile);


            FileUtils.copyInputStreamToFile(inputStream, convFile);
            try {

              final AmazonS3 s3Client = AmazonS3ClientBuilder.standard().build();
              versionId = s3Client.putObject(new PutObjectRequest("bucketName", name, convFile))
                  .getVersionId();
            } catch (final AmazonServiceException ase) {
              System.out.println("Caught an AmazonServiceException, which"
                  + " means your request made it "
                  + "to Amazon S3, but was rejected with an error response" + " for some reason.");
              System.out.println("Error Message:    " + ase.getMessage());
              System.out.println("HTTP Status Code: " + ase.getStatusCode());
              System.out.println("AWS Error Code:   " + ase.getErrorCode());
              System.out.println("Error Type:       " + ase.getErrorType());
              System.out.println("Request ID:       " + ase.getRequestId());
            } catch (final AmazonClientException ace) {
              System.out.println("Caught an AmazonClientException, which means"
                  + " the client encountered " + "an internal error while trying to "
                  + "communicate with S3, " + "such as not being able to access the network.");
              System.out.println("Error Message: " + ace.getMessage());
            }
          } catch (final Exception e) {
            log.error("You failed to upload " + name + " => " + e.getMessage());
          }

I checked this article Converting MultipartFile to java.io.File without copying to local machine but one answers says it doesn't work for File or String , while other answers doesn't have clear cut code or answer.

Please help.

Upvotes: 1

Views: 989

Answers (2)

Ankit Singh
Ankit Singh

Reputation: 345

You can do so through java as well. Below code stores the file directly to s3 without storing it locally on EC2

public boolean uploadFileDirectlyToS3(MultipartFile multipartFile, String keyName) {
        ObjectMetadata data = new ObjectMetadata();
        try {
            data.setContentType(multipartFile.getContentType());
            data.setContentLength(multipartFile.getSize());
            s3Client.putObject(CORE_BUNDLE.getString("bucket.name"), keyName, multipartFile.getInputStream(), data); 
//KeyName is the specific and unique path where you wanna place your file in s3
            return true;
        } catch (Exception e) {
            logger.error("Error occured while uploading file to s3 having name: "+multipartFile.getOriginalFilename(), e);
            return false;
        }
    }

Upvotes: 1

Shivdhwaj Pandey
Shivdhwaj Pandey

Reputation: 157

You can try using frontend directly, check the S3 documentation about directly submit of html form to s3 Check the links for reference Uploading Form Data Directly to AWS S3 - Stuff… And Things… (https://stuff-things.net/2016/03/30/uploading-form-data-directly-to-aws-s3/) Save an image file directly to S3 from a web browser using HTML5 and Backbone.js (http://www.tweetegy.com/2012/01/save-an-image-file-directly-to-s3-from-a-web-browser-using-html5-and-backbone-js/)

Upvotes: 1

Related Questions