Structured Information Extraction: GLM-OCR JSON Output for Documents
Learn how to use GLM-OCR for structured information extraction from invoices, ID cards, receipts, and forms with customizable JSON schema output.
Introduction
Information extraction transforms unstructured document images into structured data. GLM-OCR excels at extracting key information from invoices, ID cards, receipts, and forms, outputting clean JSON that integrates seamlessly with your applications.
Key Capabilities
GLM-OCR's information extraction features:
- Structured JSON Output: Returns data in predefined schema
- Custom Schema Support: Define your own extraction fields
- High Accuracy: SOTA performance on information extraction benchmarks
- Multi-Document Types: Invoices, IDs, receipts, forms, and more
Usage
Basic Information Extraction
Define a JSON schema and let GLM-OCR extract the information:
import requests
prompt = """Please extract the information from this invoice in the following JSON format:
{
"invoice_number": "",
"date": "",
"vendor": "",
"items": [
{
"description": "",
"quantity": "",
"unit_price": "",
"total": ""
}
],
"subtotal": "",
"tax": "",
"total": ""
}"""
response = requests.post(
"https://api.z.ai/api/paas/v4/layout_parsing",
headers={"Authorization": "Bearer your-api-key"},
json={
"model": "glm-ocr",
"file": "https://example.com/invoice.png",
"prompt": prompt
}
)
data = response.json()
print(data)Document Types
Invoice Extraction
{
"invoice_number": "INV-2024-001",
"date": "2024-01-15",
"vendor": {
"name": "ABC Company",
"address": "123 Business St",
"phone": "+1-555-0123"
},
"items": [
{
"description": "Widget A",
"quantity": 10,
"unit_price": 25.00,
"total": 250.00
},
{
"description": "Widget B",
"quantity": 5,
"unit_price": 50.00,
"total": 250.00
}
],
"subtotal": 500.00,
"tax": 50.00,
"total": 550.00
}ID Card Extraction
prompt = """Please extract the information from this ID card in the following JSON format:
{
"id_number": "",
"last_name": "",
"first_name": "",
"date_of_birth": "",
"address": {
"street": "",
"city": "",
"state": "",
"zip_code": ""
},
"dates": {
"issue_date": "",
"expiration_date": ""
},
"sex": ""
}"""Output:
{
"id_number": "D1234567",
"last_name": "Smith",
"first_name": "John",
"date_of_birth": "1990-05-15",
"address": {
"street": "456 Main St",
"city": "Los Angeles",
"state": "CA",
"zip_code": "90001"
},
"dates": {
"issue_date": "2020-01-01",
"expiration_date": "2028-01-01"
},
"sex": "M"
}Receipt Extraction
{
"store_name": "SuperMart",
"store_address": "789 Shopping Ave",
"date": "2024-01-20",
"time": "14:35",
"items": [
{"name": "Milk", "price": 3.99},
{"name": "Bread", "price": 2.49},
{"name": "Eggs", "price": 4.99}
],
"subtotal": 11.47,
"tax": 0.92,
"total": 12.39,
"payment_method": "Credit Card",
"card_last_four": "1234"
}Business Card Extraction
{
"name": "Jane Doe",
"title": "Senior Engineer",
"company": "Tech Corp",
"email": "[email protected]",
"phone": "+1-555-0199",
"address": "100 Tech Blvd, San Francisco, CA 94105",
"website": "www.techcorp.com"
}Custom Schema Definition
Defining Your Schema
Create schemas that match your specific needs:
# Medical prescription schema
prescription_schema = {
"patient": {
"name": "",
"date_of_birth": "",
"patient_id": ""
},
"prescriber": {
"name": "",
"license_number": "",
"clinic": ""
},
"medications": [
{
"name": "",
"dosage": "",
"frequency": "",
"duration": "",
"quantity": ""
}
],
"date_prescribed": "",
"refills": ""
}Schema Best Practices
- Be Specific: Use clear field names
- Include Types: Specify expected data types
- Handle Arrays: Use arrays for repeating items
- Nested Objects: Group related fields
Integration Examples
Database Storage
import json
import sqlite3
# Extract data
extracted_data = glm_ocr_extract(image_path, schema)
# Store in database
conn = sqlite3.connect('documents.db')
cursor = conn.cursor()
cursor.execute('''
INSERT INTO invoices (invoice_number, date, vendor, total, raw_json)
VALUES (?, ?, ?, ?, ?)
''', (
extracted_data['invoice_number'],
extracted_data['date'],
extracted_data['vendor']['name'],
extracted_data['total'],
json.dumps(extracted_data)
))
conn.commit()API Integration
from fastapi import FastAPI, UploadFile
import requests
app = FastAPI()
@app.post("/extract-invoice")
async def extract_invoice(file: UploadFile):
# Upload to temporary storage
file_url = await upload_to_storage(file)
# Extract with GLM-OCR
response = requests.post(
"https://api.z.ai/api/paas/v4/layout_parsing",
headers={"Authorization": f"Bearer {API_KEY}"},
json={
"model": "glm-ocr",
"file": file_url,
"prompt": INVOICE_SCHEMA_PROMPT
}
)
return response.json()Validation
from pydantic import BaseModel, validator
from typing import List, Optional
class InvoiceItem(BaseModel):
description: str
quantity: int
unit_price: float
total: float
@validator('total')
def validate_total(cls, v, values):
expected = values['quantity'] * values['unit_price']
if abs(v - expected) > 0.01:
raise ValueError('Total does not match quantity * unit_price')
return v
class Invoice(BaseModel):
invoice_number: str
date: str
items: List[InvoiceItem]
subtotal: float
tax: float
total: float
# Validate extracted data
extracted = glm_ocr_extract(image_path, schema)
invoice = Invoice(**extracted) # Raises ValidationError if invalidPerformance Optimization
Batch Processing
import asyncio
from concurrent.futures import ThreadPoolExecutor
async def batch_extract(documents, schema):
with ThreadPoolExecutor(max_workers=10) as executor:
loop = asyncio.get_event_loop()
tasks = [
loop.run_in_executor(
executor,
extract_document,
doc,
schema
)
for doc in documents
]
return await asyncio.gather(*tasks)Caching
import hashlib
import redis
redis_client = redis.Redis()
def extract_with_cache(image_url, schema):
# Create cache key
cache_key = hashlib.md5(
f"{image_url}:{json.dumps(schema)}".encode()
).hexdigest()
# Check cache
cached = redis_client.get(cache_key)
if cached:
return json.loads(cached)
# Extract and cache
result = glm_ocr_extract(image_url, schema)
redis_client.setex(cache_key, 3600, json.dumps(result))
return resultTroubleshooting
Common Issues
Issue: Missing fields in output Solution: Ensure the field is visible in the image and schema is correct
Issue: Incorrect data types Solution: Add type hints in your schema prompt
Issue: Poor accuracy on handwritten documents Solution: Use higher resolution images and clear handwriting
Conclusion
GLM-OCR's information extraction capabilities enable powerful document automation workflows. With customizable JSON schemas and high accuracy, you can extract structured data from virtually any document type.
Related Articles
Author
More Posts
GLM-OCR Quick Start: Complete Document Parsing Guide
Learn how to get started with GLM-OCR for document parsing. This guide covers API integration, Ollama local deployment, vLLM, and SGLang deployment options.
GLM-OCR Local Deployment: Ollama vs vLLM vs SGLang
Compare different local deployment options for GLM-OCR including Ollama, vLLM, and SGLang. Learn which option is best for your use case.
GLM-OCR: 0.9B Parameters Achieving OCR SOTA Performance
Introducing GLM-OCR, a lightweight professional OCR model with only 0.9B parameters that achieves state-of-the-art performance on OmniDocBench V1.5 with a score of 94.62.