(SpringBoot to call Textract with an Amazon S3 bucket) : error The method builder() is undefined for the type Document

Viewed 683

I am trying to call AWS Textract service in java. I have managed to work it using the local path in my desktop. However, I am having error integrating an Amazon S3 Bucket path into the application. Could you please advise?

package aws.cloud.work;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.io.InputStream;

import com.amazonaws.auth.AWSStaticCredentialsProvider;
import com.amazonaws.auth.BasicAWSCredentials;
import com.amazonaws.regions.Regions;
import com.amazonaws.services.s3.AmazonS3;
import com.amazonaws.services.s3.AmazonS3ClientBuilder;
import com.amazonaws.services.s3.model.GetObjectRequest;
import com.amazonaws.services.s3.model.S3ObjectInputStream;
import com.amazonaws.services.textract.AmazonTextract;
import com.amazonaws.services.textract.AmazonTextractClientBuilder;
import com.amazonaws.services.textract.model.DetectDocumentTextRequest;
import com.amazonaws.services.textract.model.DetectDocumentTextResult;
import com.amazonaws.services.textract.model.Document;
import com.amazonaws.services.textract.model.S3Object;
import com.amazonaws.util.IOUtils;

import software.amazon.awssdk.core.SdkBytes;

public class TextractDemo3 {

    static AmazonTextractClientBuilder clientBuilder = AmazonTextractClientBuilder.standard().withRegion(Regions.AP_SOUTH_1);

    public static void main(String[] args) throws IOException {

//Set AWS credentials       
        clientBuilder.setCredentials(new AWSStaticCredentialsProvider(new
                BasicAWSCredentials("Access key", "Secretkey")));

//**Integrating S3 Error        
//      AmazonS3 s3Client = AmazonS3ClientBuilder.standard().build();  
//      com.amazonaws.services.s3.model.S3Object s3Object = s3Client.getObject(new GetObjectRequest("textract-bucket", "image.jpg"));
//      S3ObjectInputStream s3ObjectInputStream = s3Object.getObjectContent();
//      SdkBytes bytes = SdkBytes.fromInputStream(s3ObjectInputStream);
//      Document document = Document.builder().bytes(bytes).build();

//Path to obtain image in local computer        
        String document="localpathimage";
        ByteBuffer imageBytes;

//Textract Client Service
        try (InputStream inputStream = new FileInputStream(new File(document))) {
            imageBytes = ByteBuffer.wrap(IOUtils.toByteArray(inputStream));
        }
        AmazonTextract client = clientBuilder.build();
        DetectDocumentTextRequest request = new DetectDocumentTextRequest()
                .withDocument(new Document()
                        .withBytes(imageBytes));

        DetectDocumentTextResult result = client.detectDocumentText(request);
        System.out.println(result);
        
        result.getBlocks().forEach(block ->{
            if(block.getBlockType().equals("LINE"))
            System.out.println("text is "+ block.getText() + " confidence is "+ block.getConfidence());
        });
        
    }
}

After uncommenting the S3 codes and commenting the local image path. the console returns this error

Exception in thread "main" java.lang.Error: Unresolved compilation problem: 
    The method builder() is undefined for the type Document

    at aws.cloud.work.TextractDemo3.main(TextractDemo3.java:40)
2 Answers

Your code has issues. First off, you are mixing Java V1 and V2 - which is a really bad practice. Look at this Java import statement:

import software.amazon.awssdk.core.SdkBytes;

This is a V2 API. That is, packages starting with software.amazon.... is V2. V1 packages start with com.amazonaws.services...

To get this use case to work, completely move to AWS SDK for Java V2. You can find Textract V2 examples here:

https://github.com/awsdocs/aws-doc-sdk-examples/tree/master/javav2/example_code/textract

To learn how to create a Spring BOOT app that uses AWS SDK for Java V2, see this end to end example that uses a few AWS Services:

Creating your first AWS Java web application

As shown in this example, best practice is make sure all your AWS calls use Version 2 of the Java SDK.

Because you are using Amazon S3 in your app, please refer to this example that shows how to use Amazon S3 Java V2 calls (and other AWS Services) within a Spring BOOT app. It demonstrates how to read Amazon S3 objects and pass the byte array to other services (in this example, the data is passed to Amazon Rekognition). For your use case, you need to pass the data to the Textract service.

Creating an example AWS photo analyzer application using the AWS SDK for Java

Update

I got a Spring BOOT app working perfectly for Amazon Textract and Amazon S3 using the AWS SDK for Java V2.

enter image description here

See: https://github.com/awsdocs/aws-doc-sdk-examples/tree/master/javav2/usecases/creating_document_analyzer

Thanks @smac2020 for the proper OOD java codes. Will reference that in the future.

I also finally managed to get it working with the below code with the below article:

https://github.com/awsdocs/amazon-textract-developer-guide/blob/master/doc_source/sync-calling.mdhttps://github.com/awsdocs/amazon-textract-developer-guide/blob/master/doc_source/sync-calling.md

String document="input.png";
String bucket="bucket";

AmazonTextract client = AmazonTextractClientBuilder.defaultClient();

DetectDocumentTextRequest request = new DetectDocumentTextRequest()
        .withDocument(new Document()
                .withS3Object(new S3Object()
                        .withName(document)
                        .withBucket(bucket)));

DetectDocumentTextResult result = client.detectDocumentText(request);

Working Code

package aws.cloud.work;

import java.io.IOException;
import com.amazonaws.auth.AWSStaticCredentialsProvider;
import com.amazonaws.auth.BasicAWSCredentials;
import com.amazonaws.regions.Regions;
import com.amazonaws.services.textract.AmazonTextract;
import com.amazonaws.services.textract.AmazonTextractClientBuilder;
import com.amazonaws.services.textract.model.DetectDocumentTextRequest;
import com.amazonaws.services.textract.model.DetectDocumentTextResult;
import com.amazonaws.services.textract.model.Document;
import com.amazonaws.services.textract.model.S3Object;

public class TextractOriginalMaster3 {

    static AmazonTextractClientBuilder clientBuilder = AmazonTextractClientBuilder.standard().withRegion(Regions.AP_SOUTHEAST_1);

    public static void main(String[] args) throws IOException {
       
        //Set AWS Credentials to use Textract
        clientBuilder.setCredentials(new AWSStaticCredentialsProvider(new
                BasicAWSCredentials("Accesskey", "Secretkey")));

        //**Getting document from S3 Bucket Path
        String document = "image.png";
        String bucket = "Bucket Name";

        //Calling AWS Textract Client
        AmazonTextract client = clientBuilder.build();
        DetectDocumentTextRequest request = new DetectDocumentTextRequest()
                .withDocument(new Document()
                        .withS3Object(new S3Object()
                                .withName(document)
                                .withBucket(bucket)));
        DetectDocumentTextResult result = client.detectDocumentText(request);
        System.out.println(result);
        result.getBlocks().forEach(block -> {
            if (block.getBlockType().equals("LINE"))
                System.out.println("text is " + block.getText() + " confidence is " + block.getConfidence());
        });
        
    }
}
Related