Extract text from Amazon S3

Credentials that ride in the query string, not blocked by the SSRF guard. Here's how a document actually gets from Amazon S3 to a txtfetch response.

The problem

S3 objects are private by default, so a plain object URL returns Access Denied. A presigned URL grants time-limited access instead, using the credentials of whoever generated it. No password ever appears in the URL itself.

?url=, and why

How Amazon S3 fits the decision table, cited and dated
Pre-authenticated URL?Yes — a presigned GET URL
txtfetch path?url=
Link lifetimeYour choice, set when you sign it
The trapSet the expiry longer than the async job can take, or a slow OCR pass outlives the link.

A presigned GET URL carries its credentials as query parameters. txtfetch's SSRF guard blocks credentials in a URL's userinfo, not its query string, so ?url= reaches it.

How it works

Generate a presigned GET URL for the object, with an expiry longer than the extraction can take. Pass that URL straight to txtfetch's ?url= parameter, the same as any other link. The S3-and-Lambda integration guide below wires the same call to an object-created event, so an upload triggers the extraction on its own.

the script

A plain HTTP call against Amazon S3's own REST API, then a plain call to txtfetch. No vendor SDK either side.

Python
import os

import requests

# Generate this with your own AWS credentials — see /integrations/aws-s3-lambda
# for the event-driven version. Set the expiry longer than the job can take.
presigned_url = "https://my-bucket.s3.amazonaws.com/reports/q3.pdf?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Expires=3600&X-Amz-Signature=REPLACE_ME"

r = requests.post(
    "https://api.txtfetch.com/v1/extract",
    headers={"Authorization": f"Bearer {os.environ['TXTFETCH_KEY']}"},
    params={"url": presigned_url},
)

print(r.json()["extracted_text"])
JavaScript
// Generate this with your own AWS credentials — see /integrations/aws-s3-lambda
// for the event-driven version. Set the expiry longer than the job can take.
const presignedUrl =
  "https://my-bucket.s3.amazonaws.com/reports/q3.pdf?X-Amz-Algorithm=AWS4-HMAC-SHA256&X-Amz-Expires=3600&X-Amz-Signature=REPLACE_ME";

const endpoint = new URL("https://api.txtfetch.com/v1/extract");
endpoint.searchParams.set("url", presignedUrl);

const res = await fetch(endpoint, {
  method: "POST",
  headers: { Authorization: `Bearer ${process.env.TXTFETCH_KEY}` },
});

const { extracted_text } = await res.json();
console.log(extracted_text);

txtfetch ships no connector, plugin, or client for Amazon S3. The script above is the whole integration. Fetch the document with Amazon S3's own API, then hand it to txtfetch, the same as any other source of text.

frequently asked questions

Does txtfetch have an S3 connector?
No. txtfetch ships no S3 connector or Lambda layer. A presigned URL is already a plain link, so ?url= reaches the object with no extra wiring.
Isn't a credential in the URL a security risk?
txtfetch's guard blocks credentials in a URL's userinfo, like https://user:pass@host. A presigned URL's signature lives in the query string instead, which the guard allows.
What happens if the presigned URL expires mid-request?
The fetch fails with fetch_failed, the same as any other broken link. Sign the URL for longer than the extraction, especially before an OCR-heavy scan.

Related

Point it at your Amazon S3 files.

Pass a signed URL and the text comes back. There is no connector to install.

Get an API key →

See the URL docs →