API Import

Upload endpoint, API token, status, and download endpoints.

API import lets your application upload documents directly into a workflow. It is available on Growth and Scale plans.

When to use it

  • Your product needs to submit documents automatically
  • You want server-side control over upload timing and retries
  • You need status polling and download access through the same workflow token

Configure after creation

The Add Workflow wizard only selects API Import. You must generate and store the token after the workflow is created:

  1. Go to Workflows.
  2. Find the workflow.
  3. Open the Actions menu (three dots).
  4. Click Edit.
  5. Open the Import tab.
  6. Confirm Import Method is API Import.
  7. Click Generate API token.
  8. Copy and store the token immediately.
  9. Set Attachment types.
  10. Click Save Changes.

Production endpoints

Use these production endpoints:

Endpoint Method URL
Upload POST https://api.foxello.com/api/v1/file/upload
Status GET https://api.foxello.com/api/v1/file/status/{fileId}
Download GET https://api.foxello.com/api/v1/file/download/{fileId}

Use the file ID returned by the upload response for status and download calls.

Authentication

Use the generated token with one of these headers:

  • Authorization: Bearer <token>
  • X-API-Token: <token>

The token belongs to one workflow. Any file uploaded with it is processed by that workflow.

Upload format

There are two ways to send a document to the upload endpoint.

Option 1: Send the file directly

Send files as multipart/form-data with a field named file.

Maximum file size is 5MB per upload.

curl -X POST "https://api.foxello.com/api/v1/file/upload" \
  -H "Authorization: Bearer YOUR_TOKEN" \
  -F "file=@document.pdf"

Option 2: Send a URL to fetch

If your document is already hosted somewhere reachable over the internet, send its URL instead of the file itself. Use a JSON body with a url field:

curl -X POST "https://api.foxello.com/api/v1/file/upload" \
  -H "Authorization: Bearer YOUR_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"url": "https://example.com/document.pdf"}'

The file is downloaded and streamed directly into the workflow, so it isn't limited by the multipart upload size. Maximum size is 100MB per upload.

The URL must be a public http or https address with no username/password in it, and must not redirect. URLs pointing at a private, internal, or loopback address are rejected. The URL doesn't need to end in a file extension - the file's type is detected from its content after downloading, not from the URL.

Successful uploads (either option) return 202 Accepted with file metadata. Processing continues in the background.

File type detection

The accepted document types are set in Attachment types on the Import tab. Whether you send a file directly or a URL, the type is determined by reading the file's actual content - never by trusting a filename or a URL's path - so a mislabeled or extension-less file is identified correctly rather than rejected or misprocessed.

Token safety

The token is shown only once when generated.

  • Store it in a secure secret store.
  • Do not commit it to source control.
  • Regenerate it if exposed.
  • Update all clients after regenerating, because the previous token is revoked.

Attachment types

Set accepted file types in the Import tab. Uploads with unsupported file types are rejected.

JavaScript example

const axios = require('axios');
const FormData = require('form-data');
const fs = require('fs');

const token = process.env.FOXELLO_API_TOKEN;
const form = new FormData();

form.append('file', fs.createReadStream('document.pdf'), 'document.pdf');

const upload = await axios.post(
  'https://api.foxello.com/api/v1/file/upload',
  form,
  {
    headers: {
      Authorization: `Bearer ${token}`,
      ...form.getHeaders(),
    },
  },
);

const fileId = upload.data.id;

const status = await axios.get(
  `https://api.foxello.com/api/v1/file/status/${fileId}`,
  {
    headers: {
      Authorization: `Bearer ${token}`,
    },
  },
);

console.log(status.data);

To send a URL instead of the file itself, POST a JSON body instead of a form:

const upload = await axios.post(
  'https://api.foxello.com/api/v1/file/upload',
  { url: 'https://example.com/document.pdf' },
  {
    headers: {
      Authorization: `Bearer ${token}`,
      'Content-Type': 'application/json',
    },
  },
);

Python example

import os
import requests

token = os.environ["FOXELLO_API_TOKEN"]

with open("document.pdf", "rb") as document:
    upload = requests.post(
        "https://api.foxello.com/api/v1/file/upload",
        headers={"Authorization": f"Bearer {token}"},
        files={"file": document},
        timeout=60,
    )

upload.raise_for_status()
file_id = upload.json()["id"]

status = requests.get(
    f"https://api.foxello.com/api/v1/file/status/{file_id}",
    headers={"Authorization": f"Bearer {token}"},
    timeout=30,
)

status.raise_for_status()
print(status.json())

To send a URL instead of the file itself, POST a JSON body instead of a form:

upload = requests.post(
    "https://api.foxello.com/api/v1/file/upload",
    headers={"Authorization": f"Bearer {token}"},
    json={"url": "https://example.com/document.pdf"},
    timeout=30,
)

Download example

Download only after the file reaches processed, approved, or exported status.

curl -X GET "https://api.foxello.com/api/v1/file/download/FILE_ID" \
  -H "Authorization: Bearer YOUR_TOKEN" \
  --output result

See API Integration for the full upload, status, and download workflow.

Need more help?

Signed-in users can reach our team from Support in the app, or contact us.

Ready to try it on your own documents?

Create a workflow, upload a document, and see structured results in minutes.

Start free - no card