> ## Documentation Index
> Fetch the complete documentation index at: https://docs.anyformat.ai/llms.txt
> Use this file to discover all available pages before exploring further.

# Receipt Scanning

> Extract totals from receipt photos

## Workflow fields

<Tip>
  We recommend creating this workflow in the [anyformat platform](https://app.anyformat.ai) where you can test with sample receipt photos and iterate on field descriptions. Copy the workflow ID to use with the API.
</Tip>

| Field              | Type    | Description                   |
| ------------------ | ------- | ----------------------------- |
| `store_name`       | string  | Name of the store or merchant |
| `store_address`    | string  | Store location                |
| `receipt_date`     | date    | Date of purchase              |
| `total_amount`     | float   | Total amount charged          |
| `tax_amount`       | float   | Tax amount                    |
| `number_of_items`  | integer | Number of items purchased     |
| `payment_method`   | enum    | How the purchase was paid     |
| `contains_alcohol` | boolean | Whether alcohol was purchased |

## End-to-end

<Tabs>
  <Tab title="curl" icon="terminal">
    ```bash theme={null}
    # 1. Create the workflow
    curl -X POST 'https://api.anyformat.ai/v2/workflows/' \
      -H 'Content-Type: application/json' \
      -H "Authorization: Bearer $ANYFORMAT_API_KEY" \
      -d '{
        "name": "Receipt Scanner",
        "description": "Extract receipt details from photos and scans",
        "nodes": [
          {"id": "parse_1", "type": "parse"},
          {
            "id": "extract_1",
            "type": "extract",
            "extraction_schema": {
              "fields": [
                {"name": "store_name",       "description": "Name of the store or merchant",          "data_type": "string"},
                {"name": "store_address",    "description": "Full address of the store location",     "data_type": "string"},
                {"name": "receipt_date",     "description": "Date of the purchase transaction",       "data_type": "date"},
                {"name": "total_amount",     "description": "Total amount charged including tax",     "data_type": "float"},
                {"name": "tax_amount",       "description": "Total tax amount",                       "data_type": "float"},
                {"name": "number_of_items",  "description": "Total number of items purchased",        "data_type": "integer"},
                {
                  "name": "payment_method",
                  "description": "Payment method used for the transaction",
                  "data_type": "enum",
                  "enum_options": [
                    {"name": "cash",            "description": "Cash payment"},
                    {"name": "credit_card",     "description": "Credit card payment"},
                    {"name": "debit_card",      "description": "Debit card payment"},
                    {"name": "mobile_payment",  "description": "Mobile or digital wallet payment"}
                  ]
                },
                {"name": "contains_alcohol", "description": "Whether any alcoholic beverage was included in the purchase", "data_type": "boolean"}
              ]
            }
          }
        ],
        "edges": [{"source": "parse_1", "target": "extract_1"}]
      }'

    # 2. Run a receipt photo
    curl -X POST 'https://api.anyformat.ai/v2/workflows/WORKFLOW_ID/run/' \
      -H "Authorization: Bearer $ANYFORMAT_API_KEY" \
      -F 'file=@receipt.jpg'

    # 3. Poll for results
    curl -H "Authorization: Bearer $ANYFORMAT_API_KEY" \
      'https://api.anyformat.ai/v2/workflows/WORKFLOW_ID/files/COLLECTION_ID/results/'
    ```
  </Tab>

  <Tab title="TypeScript" icon="js" iconType="brands">
    ```typescript theme={null}
    import { Anyformat, Schema } from "@anyformat/sdk";

    const af = new Anyformat({ apiKey: process.env.ANYFORMAT_API_KEY! });
    const file: File = /* a File with .name set, e.g. new File([bytes], "receipt.jpg") */;

    const workflow = await af
      .workflow("Receipt Scanner", "Extract receipt details from photos and scans")
      .parse()
      .extract([
        Schema.string("store_name",       "Name of the store or merchant"),
        Schema.string("store_address",    "Full address of the store location"),
        Schema.date("receipt_date",       "Date of the purchase transaction"),
        Schema.float("total_amount",      "Total amount charged including tax"),
        Schema.float("tax_amount",        "Total tax amount"),
        Schema.integer("number_of_items", "Total number of items purchased"),
        Schema.enum("payment_method", "Payment method used for the transaction", [
          Schema.option("cash",           "Cash payment"),
          Schema.option("credit_card",    "Credit card payment"),
          Schema.option("debit_card",     "Debit card payment"),
          Schema.option("mobile_payment", "Mobile or digital wallet payment"),
        ]),
        Schema.boolean("contains_alcohol", "Whether any alcoholic beverage was included"),
      ])
      .create();

    const run = await workflow.run(file);
    const result = await run.wait();

    console.log(result.field("store_name")?.value);
    console.log(result.field("total_amount")?.value);
    console.log(result.field("contains_alcohol")?.value);
    ```
  </Tab>

  <Tab title="Python" icon="python" iconType="brands">
    ```python theme={null}
    import os
    from anyformat.sdk import Client
    from anyformat.workflow import Schema

    client = Client(api_key=os.environ["ANYFORMAT_API_KEY"])

    workflow = (
        client.workflow("Receipt Scanner")
        .parse()
        .extract([
            Schema.string("store_name",       "Name of the store or merchant"),
            Schema.string("store_address",    "Full address of the store location"),
            Schema.date("receipt_date",       "Date of the purchase transaction"),
            Schema.float("total_amount",      "Total amount charged including tax"),
            Schema.float("tax_amount",        "Total tax amount"),
            Schema.integer("number_of_items", "Total number of items purchased"),
            Schema.enum("payment_method", "Payment method used for the transaction", options=[
                Schema.option("cash",           "Cash payment"),
                Schema.option("credit_card",    "Credit card payment"),
                Schema.option("debit_card",     "Debit card payment"),
                Schema.option("mobile_payment", "Mobile or digital wallet payment"),
            ]),
            Schema.boolean("contains_alcohol", "Whether any alcoholic beverage was included"),
        ])
        .create()
    )

    result = workflow.run("receipt.jpg").wait()

    print(result.fields["store_name"].value)
    print(result.fields["total_amount"].value)
    print(result.fields["contains_alcohol"].value)
    ```
  </Tab>
</Tabs>

## Tips

* For receipt photos, good lighting and a flat surface produce significantly better results.
* PNG images generally extract better than compressed JPG. If quality matters, prefer PNG.
* `enum` with explicit options constrains the output to known values, preventing free-text variations like "Visa" vs "credit card" vs "CC".

## Next steps

<CardGroup cols={2}>
  <Card title="Response formats" icon="list" href="/api-reference/response-formats">
    The unified JSON response shape
  </Card>

  <Card title="Errors" icon="triangle-exclamation" href="/api-reference/errors">
    Handle rate limits and retries in production
  </Card>
</CardGroup>
