This application demonstrates how to use AWS Textract's AnalyzeDocument API (FORMS feature) to parse PDF forms, extract structured Key-Value pairs (including checkboxes), and display them in an Angular frontend.
- Frontend: Angular 21+ (Standalone Components), TypeScript, CSS (Flexbox/Grid).
- Backend: Node.js, Express.js.
- AWS Services:
- Amazon Textract: Specifically the
StartDocumentAnalysisAPI withFeatureTypes: ["FORMS"]for structured data extraction. - Amazon S3: For temporary storage of documents required by the asynchronous Textract API.
- Amazon Textract: Specifically the
- Libraries:
@aws-sdk/client-textract: For interacting with Textract.@aws-sdk/client-s3: For uploading files to S3.multer: For handling file uploads in Express.
The application follows a standard asynchronous processing flow to handle potentially multi-page PDF documents:
-
File Upload:
- The user selects a PDF in the Angular frontend.
- The file is sent to the Node.js backend via the
/analyzeendpoint usingFormData.
-
S3 Staging:
- The backend uploads the received file to a designated Amazon S3 Bucket.
- This step is necessary because the asynchronous
StartDocumentAnalysisAPI requires the input document to be in an S3 bucket (it cannot accept raw bytes for large files).
-
Textract Analysis Job:
- The backend initiates a Textract job using
StartDocumentAnalysisCommand. - Key Configuration:
FeatureTypes: ["FORMS"]is enabled. This tells Textract to specifically look for key-value pairs (e.g., "Name: John Doe") and selection elements (checkboxes).
- The backend initiates a Textract job using
-
Polling Validation:
- The backend polls the
GetDocumentAnalysisCommandAPI every 1 second to check the Job Status. - Once the status changes to
SUCCEEDED, the backend retrieves all result pages (handling pagination/NextToken).
- The backend polls the
-
Data Parsing & Structured Output:
- The raw Textract JSON response consists of thousands of "Blocks" (
PAGE,LINE,WORD,KEY_VALUE_SET,SELECTION_ELEMENT). - Data Parsing & Schema Validation:
- Fuzzy Matching: extracted keys are compared against a canonical
generated_schema.jsonusing Levenshtein distance. This corrects OCR typos (e.g.Sentenc Date->Sentence Date) and ensures consistent JSON keys. - Boolean Extraction: The parser specifically detects fields that contain checkboxes (Selection Elements). Even if a field contains mixed text (e.g.,
[ ] (Less than...)), the logic extracts the boolean state (true/false) while ignoring the noise. - Pruning: Extraneous page elements (Footers, Page numbers) defined in the schema are automatically filtered out.
- Fuzzy Matching: extracted keys are compared against a canonical
- Schema Enforcement:
generated_schema.jsonacts as a strict contract, defining not just the keys but the types (e.g.,booleanfor checkboxes). This ensures the frontend receives predictable, type-safe data.
- The raw Textract JSON response consists of thousands of "Blocks" (
-
Response:
- The backend returns a unified JSON object containing both the raw
Blocks(for the visual overlay) and the cleanedStructuredData(for the form table). - The Angular UI renders the text overlay on the PDF and populates the data table.
- The backend returns a unified JSON object containing both the raw
- Purpose: Extracts structured form data with schema validation.
- Input:
multipart/form-datawithfile(PDF). - Output: JSON object
{ "StructuredData": { ... } }. - Details: Returns simplified, normalized key-value pairs matching
generated_schema.json.
- Purpose: Returns raw Textract blocks for visual overlays.
- Input:
multipart/form-datawithfile(PDF). - Output: JSON object
{ "Blocks": [ ... ] }. - Details: Returns the full hierarchy of PAGE, LINE, WORD keywords and bounding boxes.
- Node.js: v24+ installed.
- AWS Account: Active account with permissions to manage Textract and S3.
- IAM Permissions: Ensure your user has
AmazonTextractFullAccessandAmazonS3FullAccess. - S3 Bucket: Create a bucket (e.g.,
textract-demo-bucket) in your region (e.g.,us-east-1).
Create a .env file in the root folder (textract_sample/.env):
AWS_ACCESS_KEY_ID=your_access_key_id
AWS_SECRET_ACCESS_KEY=your_secret_access_key
AWS_REGION=us-east-1
BUCKET_NAME=your_existing_s3_bucket_namecd textract_sample
npm install
node server.js- Server starts on port 3001.
cd textract_sample/textract-demo
npm install
ng serve- Access the app at
http://localhost:4200.