# GLB to USDZ Converter - AR Quick Look Ready (API) (`sergeyfaraday/glb-to-usdz`) Actor

Convert GLB/glTF to USDZ via API - no Mac, no Xcode. Every file is validated against Apple's ARKit rules and shipped with a QC report: correct PBR materials, Draco/KTX2 support, batch mode, previews, n8n & MCP ready. Fair billing: no valid file, no conversion charge.

- **URL**: https://apify.com/sergeyfaraday/glb-to-usdz.md
- **Developed by:** [Sergey Faraday](https://apify.com/sergeyfaraday) (community)
- **Categories:** Developer tools, Integrations
- **Stats:** 1 total users, 0 monthly users, 100.0% runs succeeded, 2 bookmarks
- **User rating**: 5.00 out of 5 stars

## Pricing

from $90.00 / 1,000 conversion successes

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.
Since this Actor supports Apify Store discounts, the price gets lower the higher subscription plan you have.

Learn more: https://docs.apify.com/actors/running/actors-in-store.md#pay-per-event

## What's an Apify Actor?

Actors are web data automations that power AI and operations. They run on the Apify platform to scrape websites, process data, connect APIs, and automate workflows.
In Batch mode, an Actor accepts a well-defined JSON input, performs an action which can take anything from a few seconds to a few hours,
and optionally produces a well-defined JSON output, datasets with results, or files in key-value store.
In Standby mode, an Actor provides a web server which can be used as a website, API, or an MCP server.
Actors are written with capital "A".

## How to integrate an Actor?

If asked about integration, you help developers integrate Actors into their projects.
You adapt to their stack and deliver integrations that are safe, well-documented, and production-ready.
The best way to integrate Actors is as follows.

- **AI agents and MCP clients** — the [Apify MCP server](https://docs.apify.com/integrations/mcp.md) at `https://mcp.apify.com` (remote, streamable HTTP, OAuth on first use).
- **Agentic workflows and local Actor development** — [Agent Skills](https://apify.com/.well-known/agent-skills/index.json) with the [Apify CLI](https://docs.apify.com/cli/docs.md): `npm install -g apify-cli`, then `apify login`.
- **JavaScript/TypeScript projects** — the official [JS/TS client](https://docs.apify.com/api/client/js/docs.md): `npm install apify-client`.
- **Python projects** — the official [Python client](https://docs.apify.com/api/client/python/docs.md): `pip install apify-client`.
- **Any other language** — the [REST API](https://docs.apify.com/api/v2.md).

For usage examples, see the [API](#api) section below.

For more details, see Apify documentation as [Markdown index](https://docs.apify.com/llms.txt) and [Markdown full-text](https://docs.apify.com/llms-full.txt).

# README

## GLB to USDZ Converter - AR Quick Look Ready

Convert GLB and glTF to USDZ that opens correctly in Apple AR Quick Look - via API, no Mac required. Every file is ARKit-validated and returned with a machine-readable QC report, so what you ship to iPhone, iPad, and visionOS is checked before you pay for it.

Apple has retired its `usdzconvert` / USDPython tools, and the free browser converters run client-side with no API - a pipeline, a CI job, or an AI agent can't click a browser button. This Actor is the server-side path: URL in, validated `.usdz` and report out.

### Quick start

```bash
curl -X POST "https://api.apify.com/v2/acts/YOUR_USERNAME~glb-to-usdz/run-sync-get-dataset-items?token=YOUR_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"source": ["https://example.com/model.glb"]}'
```

For files that may take over a minute, use the async flow instead - see [n8n integration](#n8n-integration) below.

### Convert GLB to USDZ in Python - the usdzconvert replacement

Apple's `usdzconvert` / USDPython toolchain is discontinued, and it only ever ran on macOS. To convert GLB to USDZ in Python now, on any OS, call the Actor with the official client:

```python
from apify_client import ApifyClient

client = ApifyClient("YOUR_TOKEN")
run = client.actor("YOUR_USERNAME/glb-to-usdz").call(
    run_input={"source": ["https://example.com/model.glb"], "textureMaxSize": 2048},
)
for item in client.dataset(run["defaultDatasetId"]).iterate_items():
    print(item["status"], item["arkitCompatible"], item["usdzUrl"])
```

No Blender scripting, no OpenUSD compilation, no `usd_from_gltf` build headaches - the USD toolchain runs inside the Actor.

### No Mac? No Xcode? No problem

Reality Converter is a macOS GUI app. `usdzconvert` required a Mac and is now retired. This Actor converts GLB to USDZ **on Windows, Linux, CI runners, and serverless pipelines** - anywhere you can make an HTTP request. If you've been keeping a Mac mini alive just to produce USDZ files for iOS AR, you can retire it.

### Sample report

Each input file produces one dataset row:

```json
{
  "schemaVersion": "1.0",
  "converterVersion": "1.2.0",
  "source": "https://example.com/model.glb",
  "fileIndex": 0,
  "status": "ok_with_warnings",
  "arkitCompatible": true,
  "usdzUrl": "https://api.apify.com/v2/key-value-stores/STORE_ID/records/usdz-abc123.usdz",
  "previewUrl": null,
  "validation": {
    "gate": "ARKit ComplianceChecker",
    "gateVersion": "25.11",
    "errors": 0,
    "warnings": 0
  },
  "issues": [],
  "warnings": [
    { "code": "MORPH_STRIPPED", "message": "Morph targets are not supported and were removed." }
  ],
  "stats": {
    "inputSizeMB": 4.2,
    "outputSizeMB": 3.8,
    "triangles": 12400,
    "meshes": 3,
    "materials": 2,
    "textures": [
      { "name": "albedo", "from": "png 4096x4096", "to": "jpeg 2048x2048", "width": 2048, "height": 2048, "files": 1 }
    ],
    "animations": { "kept": 1, "stripped": 0, "resampled": 1, "skelStripped": 0 },
    "unitScaleApplied": 1
  },
  "timings": {
    "fetchSec": 0.8,
    "preprocessSec": 1.2,
    "convertSec": 3.4,
    "uploadSec": 0.3,
    "totalSec": 5.7
  },
  "idempotencyKey": "sha256:abc123..."
}
```

`status` is `ok` only when the row carries no warnings at all; any warning - even a harmless stripped morph target - makes it `ok_with_warnings`, and a missing deliverable makes it `failed`.

### Validate an existing USDZ file

Already have a `.usdz` that "doesn't work in AR"? Run it through the same ARKit compliance checker without converting anything - $0.03 per file:

```bash
curl -X POST "https://api.apify.com/v2/acts/YOUR_USERNAME~glb-to-usdz/run-sync-get-dataset-items?token=YOUR_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"mode": "validateOnly", "source": ["https://example.com/model.usdz"]}'
```

The row comes back with `arkitCompatible`, the gate's error/warning counts, and every finding as a coded issue. Works for USDZ files produced by any tool, and for `.usdz` records in your own key-value store (`uploadStore` + `uploadRecords`; API names `sourceKeyValueStore` / `sourceKeys` still accepted).

### Does it keep animations?

Honest answer, because most converters break here:

- **Transform animations** (translation / rotation / scale clips) - **preserved**, resampled to LINEAR at 30 fps and exported as USD time samples. Product turntables, hovering objects, opening lids survive.
- **Skeletal (rigged) animation** - the mesh is converted at a clean bind pose with an explicit `SKEL_STRIPPED` warning. UsdSkel authoring is on the roadmap; we don't silently ship broken rigs.
- **Morph targets / blend shapes** - not supported by AR Quick Look; stripped with a `MORPH_STRIPPED` warning, never silently.

Every degradation is a named warning code in the report. You always know what changed.

### glTF to USDZ - including multi-file scenes

**Multi-file glTF scenes (`.gltf` + external `.bin` + textures) are supported: submit them as a zip, or as a `.gltf` URL whose relative resources resolve automatically.** Binary `.glb` works as-is. Draco- and meshopt-compressed meshes are decoded; KTX2/Basis and WebP textures are transcoded to USDZ-compatible PNG/JPEG with size limits you control.

### ARKit validation - because "converted" is not "working"

A `.usdz` that opens on your desktop can still fail on an iPhone. Every output here runs through Apple's ARKit compliance checker (from OpenUSD) before you're charged for it:

- `arkitCompatible: true/false` on every file, from the real checker - not a guess
- `failOn: error | warning | never` - you choose whether non-compliant files are delivered
- `mode: reportOnly` - validate the whole conversion pipeline for $0.03 without buying the file

### Why your USDZ looks wrong in AR Quick Look

#### USDZ model appears black or plastic

Metallic-roughness channels must be split into separate grayscale inputs for `UsdPreviewSurface`; naive converters wire the packed ORM texture straight in and get shiny black plastic. This Actor splits the channels, sets the color space per texture (sRGB for color, raw for data), and folds `normalScale` / `occlusionStrength` into the texture network instead of dropping them.

#### Model is 100× too big (or too small) in AR

glTF is meters; many DCC exports aren't. Rather than silently rescaling your geometry, the report tells you the applied factor and warns on a suspicious scene size (`SUSPICIOUS_SCALE`). Fix it in one option: `targetHeight: 1.5` ("make it 1.5 m tall"), or `sourceUnits: "cm"` if you know what the DCC exported.

#### GLB with animation breaks in USDZ

Transform clips are kept; skeletal rigs and morph targets are the parts Quick Look can't play, and they are removed with named warnings instead of producing a frozen or exploded mesh. Set `animation: strip` if you want a static asset on purpose.

#### Symptom → cause → where to look

| Symptom | What happened | What to check |
|---|---|---|
| Model invisible or black | Missing or incompatible materials | `issues[]` for material codes |
| Wrong scale (tiny/huge) | Unit mismatch | `stats.unitScaleApplied`, try `sourceUnits` (e.g. `"cm"`) or `targetHeight` |
| No textures | Source uses KTX2/WebP without extensions | `warnings[]` for texture codes |
| Transparency broken | Alpha mode incompatibility | Try `alphaHandling: forceOpaque` |
| Missing animation | Non-transform animation stripped | `warnings[]` for `SKEL_STRIPPED` |
| Morph targets gone | Not supported by USDZ/ARKit | `warnings[]` for `MORPH_STRIPPED` |
| Dark/flat appearance | Unlit material approximated | `warnings[]` for `UNLIT_APPROXIMATED` |
| Sheen/transmission approximated | Mapped onto opacity/roughness (no refraction) | `warnings[]` for `TRANSMISSION_APPROXIMATED` / `SHEEN_APPROXIMATED` |
| Specular strength approximated | Folded into `ior` (tint averaged) | `warnings[]` for `SPECULAR_APPROXIMATED` |
| Anisotropy/iridescence lost | No UsdPreviewSurface equivalent | `warnings[]` for `ANISOTROPY_DROPPED` / `IRIDESCENCE_DROPPED` |
| Wrong orientation / tiling | Coordinate system or texture transform | `stats.textures`; `KHR_texture_transform` is authored as `UsdTransform2d` with the UV flip |
| File won't open in Quick Look at all | Package layout | Packaged through the official USD API (uncompressed, aligned) - check `issues[]` for gate errors |
| Gate errors on valid model | Strict compliance check | Set `failOn: never` to deliver anyway |
| File too large | Input exceeds 250 MB limit | Split model or reduce textures |
| SSRF blocked | Private/loopback URL rejected | Use a public URL or KVS input |

### Fair billing

**A failed conversion never bills `conversion-success`.** Early failures (bad URL, not a GLB, SSRF blocked, too large, empty scene) bill nothing - $0. Actor start is free.

| Path | Price | When |
|---|---|---|
| Conversion success (≤ 50 MB) | $0.12 | USDZ delivered to KV store |
| Large file surcharge (> 50 MB) | +$0.10 | On top of conversion-success |
| Preview render | +$0.02 | `outputPreview: true` and the PNG was actually delivered |
| Validation report only | $0.03 | `reportOnly` / `validateOnly` mode, or `failOn`-driven USDZ withholding |
| Dedup hit | $0 | Same file+options already converted in this run |
| Early failure | $0 | Fetch/sniff/preprocess error, budget exhausted |

Every output is validated for AR Quick Look using the ARKit ComplianceChecker from OpenUSD.

### Output retention

Output URLs are temporary run artifacts - copy the USDZ to permanent storage. The `usdzUrl` in each report row points to a key-value store record that expires with the run's default retention period. Your models live only in your run's storage under your account; there is no public gallery and no reuse.

### MCP / agent integration

This Actor is exposed under the slug **`glb-to-usdz`** via Apify's Actor-MCP bridge - callable as a tool from Claude, Cursor, and any MCP client. When calling it as an MCP tool:

- For one model, pass a single-item `source` array
- Latency is seconds to about a minute per file depending on size and texture count
- On a `status: failed` result, surface `issues[]` to the user - do not blind-retry
- Check `arkitCompatible` and `warnings[]` before presenting the result as successful
- The `usdzUrl` is temporary; if the user needs to keep the file, copy it

### n8n integration

Use the **async chain** as the primary recipe - the sync endpoint's ~300 s limit sits at the per-file deadline, so large files on the sync path appear as broken integrations.

1. **Start run** - `POST /v2/acts/YOUR_USERNAME~glb-to-usdz/runs` with input JSON
2. **Poll status** - `GET /v2/actor-runs/{runId}` until `status` is `SUCCEEDED` or `FAILED`
3. **Get results** - `GET /v2/datasets/{defaultDatasetId}/items`
4. **Download USDZ** - `GET` the `usdzUrl` from each row (no token needed, public URL)

For small files under 1 minute, the synchronous endpoint works:
`POST /v2/acts/YOUR_USERNAME~glb-to-usdz/run-sync-get-dataset-items`

An n8n workflow template is available at `templates/n8n/glb-to-usdz.json`. The same recipe fits Make, CI (convert and validate 3D assets on every commit), and e-commerce back ends that generate AR Quick Look assets for every uploaded product model.

### Input schema

| Field | Type | Default | Notes |
|---|---|---|---|
| `uploadedModels` | string\[] | null | Files dropped into the console's upload widget (`.glb` / `.gltf` / `.zip`); no API needed. Combines with the inputs below |
| `source` | string\[] | null | URL(s) to GLB/glTF/ZIP files. Batch up to 200. |
| `uploadStore` | string | null | Apify KVS to read files from, or the store an upload landed in (grants read access to a limited-permission run); combines with `source` / `uploadedModels`. Legacy API name `sourceKeyValueStore` still accepted |
| `uploadRecords` | string\[] | null | Record names inside the granted store; optional when the store is only granting access for `uploadedModels`. Legacy API name `sourceKeys` still accepted |
| `mode` | `convert` | `reportOnly` | `validateOnly` | `convert` | `reportOnly`: full pipeline, report only, no USDZ ($0.03). `validateOnly`: validate an existing `.usdz` (URL or KVS record), no conversion ($0.03) |
| `textureMaxSize` | integer 256-4096 | 2048 | Max texture dimension (longest side); 1024 / 2048 / 4096 are the useful stops |
| `textureFormat` | `auto` | `png` | `jpeg` | `auto` | Color textures only; data textures always PNG |
| `unitScale` | `auto` | `asIs` | number | `auto` | Meters-per-unit scale factor |
| `sourceUnits` | `mm` | `cm` | `m` | `inches` | `feet` | null | Units the model was authored in; resolves to the numeric scale for you. `targetHeight` takes precedence if both are set (`SCALE_OPTION_OVERRIDDEN` warning) |
| `targetHeight` | number | null | Desired model height (in `targetHeightUnit`, meters by default); the converter measures the bounding box and computes the scale. Wins over `sourceUnits` and numeric `unitScale` (`SCALE_OPTION_OVERRIDDEN` warning) |
| `targetHeightUnit` | `m` | `cm` | `mm` | `inches` | `feet` | `m` | Unit of `targetHeight`; converted to meters before processing, so `150 cm` and `1.5 m` are the same job |
| `animation` | `preserve` | `strip` | `preserve` | Transform animations only |
| `alphaHandling` | `preserve` | `forceOpaque` | `preserve` | Force opaque discards alpha |
| `failOn` | `error` | `warning` | `never` | `error` | Controls USDZ delivery on gate findings |
| `outputPreview` | boolean | false | Render a flat 800×800 transparent PNG preview alongside the USDZ (+$0.02). A failed render never blocks the USDZ |
| `targetMaxFileSizeMB` | number | null | Warn (`TARGET_SIZE_EXCEEDED`) when the output USDZ exceeds this size; `failOn` decides delivery |
| `webhookUrl` | string | null | POST the batch summary to this URL when the run completes |

#### Getting the size right in AR

Three user-friendly ways to fix a model that shows up tiny or huge in Quick Look, in order of preference:

1. **`targetHeight: 1.5`** - "make it 1.5 m tall". No unit archaeology needed.
2. **`sourceUnits: "cm"`** - you know the DCC exported centimeters.
3. **`unitScale: 0.01`** - the raw numeric factor, for scripts that computed it themselves.

Quick Look's AR texture budget: keep textures ≤ 2048×2048 and ≤ 6 total. The report warns with `AR_TEXTURE_BUDGET_WARNING` when the output exceeds Apple's recommendation.

#### Quick Look embedding tip

Lighting in AR Quick Look is controlled on the *embed side*, not inside the USDZ. When linking a USDZ on the web, you can pin the newer image-based lighting for glossier, more accurate materials:

```html
<a rel="ar" href="model.usdz#preferredIblVersion=2">View in AR</a>
```

### FAQ

**How do I convert GLB to USDZ without a Mac?**
Call this Actor from any OS via HTTP (or the Python client above) - the USD toolchain runs server-side. No Reality Converter, no Xcode, no macOS.

**Is Apple's usdzconvert still available?**
No - Apple has retired its Python USDZ tools. This Actor is a maintained server-side replacement with ARKit validation on top.

**Does GLB to USDZ conversion keep animations?**
Transform animations, yes. Skeletal rigs are converted at bind pose with a warning; morph targets aren't supported by AR Quick Look and are stripped with a warning.

**What does "ARKit validated" mean?**
Every file runs through Apple's ARKit compliance checker inside the Actor. The report says `arkitCompatible: true` only when the checker finds zero errors - that is what makes the file safe for iOS, iPadOS, and visionOS Quick Look.

**Can I check a USDZ I already have?**
Yes - `mode: validateOnly` runs the same gate on an existing `.usdz` for $0.03, no conversion.

**Are my models stored?**
Only in your run's Apify storage, under your account's retention settings. There is no public gallery and no reuse of your models.

### Current limits and roadmap

Skeletal (UsdSkel) animation authoring, FBX/OBJ/STL inputs, and USDZ→GLB reverse conversion are not in this version - they are tracked publicly on the roadmap. Previews, validation of existing USDZ files, and multi-file glTF input are already here.

# Actor input Schema

## `uploadedModels` (type: `array`):

Drop **.glb**, **.gltf**, or **.zip** (multi-file glTF set) straight from your computer. **One-time setup:** in the upload dialog choose **New permanent storage** and name it (e.g. `glb-uploads`); from then on pick **Existing storage -> glb-uploads** every time, and select the same `glb-uploads` in the field right below. The Actor runs with limited permissions and can only read stores you grant this way. The .usdz lands in the run's **Storage -> Key-value store**.

## `uploadStore` (type: `string`):

Pick the storage your upload went into (by name from the list). Without this grant, uploaded files fail with UPLOAD\_NOT\_READABLE naming the store to pick. Pipelines can also use this store as an input source - list the records under Advanced -> Records inside the granted store. (API name until 1.2: sourceKeyValueStore - still accepted.)

## `source` (type: `array`):

Direct link(s) to .glb / .gltf / .zip files. Up to 200 per run (batch). The prefill is a public Khronos sample - replace it with your own.

## `targetHeight` (type: `number`):

Type the real-world height and pick the unit right below: **1.5 m** for a person-sized figure, **30 cm** for a toy, **8 cm** for a mug. The converter measures the model and scales it to match. Leave empty to keep the size as authored (with a warning if it looks off).

## `targetHeightUnit` (type: `string`):

The unit for the number in Target height. Ignored when Target height is empty.

## `textureMaxSize` (type: `string`):

Longest side. Textures above this are resized. Apple recommends 2048 or less for smooth AR Quick Look.

## `textureFormat` (type: `string`):

USDZ accepts only PNG/JPEG; KTX2/Basis/WebP inputs are transcoded automatically. Data textures (normal, metallic, roughness, occlusion) always stay PNG.

## `alphaHandling` (type: `string`):

If glass/foliage renders oddly on device, try force opaque.

## `animation` (type: `string`):

Applies to translation/rotation/scale clips. Skeletal rigs are converted at bind pose and morph targets are removed (AR Quick Look doesn't support them) - always with an explicit warning in the report.

## `mode` (type: `string`):

"Validate" mode accepts .usdz files as input (URL, upload, or store record) and answers: will this open correctly in AR Quick Look?

## `failOn` (type: `string`):

Every output is checked with Apple's ARKit compliance rules. This controls whether a non-compliant file is still delivered.

## `outputPreview` (type: `boolean`):

**+$0.02 per image.** Flat 800x800 transparent render of the converted model so you can eyeball the result without an iPhone. A failed render never blocks your USDZ.

## `unitScale` (type: `string`):

For scripts: "auto" (default; warns on suspicious size, never rescales silently), "asIs" (skip the sanity check), or a numeric factor like "0.01". Target height and Source units take precedence over this factor (with a warning).

## `uploadRecords` (type: `array`):

Convert these records (by record name) from the store selected in "Grant access to the upload store". Not needed for uploads. (API name until 1.2: sourceKeys - still accepted.)

## `sourceUnits` (type: `string`):

Alternative to Target height for scripts: declare the export units (e.g. the DCC exported centimeters) to keep the authored size. If Target height is set, it wins and this is ignored with a warning.

## `targetMaxFileSizeMB` (type: `number`):

Emits TARGET\_SIZE\_EXCEEDED when the .usdz is larger than this; failOn decides delivery. Apple's practical guidance for web AR is 25 MB or less.

## `webhookUrl` (type: `string`):

POST the batch summary JSON here when the run completes. Stored encrypted (webhook URLs often carry tokens); never shown in logs or on task pages.

## Actor input object example

```json
{
  "source": [
    "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF-Binary/DamagedHelmet.glb"
  ],
  "targetHeightUnit": "m",
  "textureMaxSize": "2048",
  "textureFormat": "auto",
  "alphaHandling": "preserve",
  "animation": "preserve",
  "mode": "convert",
  "failOn": "error",
  "outputPreview": false,
  "unitScale": "auto"
}
```

# Actor output Schema

## `conversionReports` (type: `string`):

One row per input file with status, ARKit compliance, artifact URL, validation, stats, and timings.

## `usdzArtifacts` (type: `string`):

Converted USDZ files ready for AR Quick Look download.

## `previews` (type: `string`):

Flat PNG previews of converted models (when outputPreview is enabled).

# API

You can run this Actor programmatically using our API. Below are code examples in JavaScript, Python, and CLI, as well as the OpenAPI specification and MCP server setup.

## JavaScript example

```javascript
import { ApifyClient } from 'apify-client';

// Initialize the ApifyClient with your Apify API token
// Replace the '<YOUR_API_TOKEN>' with your token
const client = new ApifyClient({
    token: '<YOUR_API_TOKEN>',
});

// Prepare Actor input
const input = {
    "source": [
        "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF-Binary/DamagedHelmet.glb"
    ]
};

// Run the Actor and wait for it to finish
const run = await client.actor("sergeyfaraday/glb-to-usdz").call(input);

// Fetch and print Actor results from the run's dataset (if any)
console.log('Results from dataset');
console.log(`💾 Check your data here: https://console.apify.com/storage/datasets/${run.defaultDatasetId}`);
const { items } = await client.dataset(run.defaultDatasetId).listItems();
items.forEach((item) => {
    console.dir(item);
});

// 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/js/docs

```

## Python example

```python
from apify_client import ApifyClient

# Initialize the ApifyClient with your Apify API token
# Replace '<YOUR_API_TOKEN>' with your token.
client = ApifyClient("<YOUR_API_TOKEN>")

# Prepare the Actor input
run_input = { "source": ["https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF-Binary/DamagedHelmet.glb"] }

# Run the Actor and wait for it to finish
run = client.actor("sergeyfaraday/glb-to-usdz").call(run_input=run_input)

# Fetch and print Actor results from the run's dataset (if there are any)
print(f"💾 Check your data here: https://console.apify.com/storage/datasets/{run.default_dataset_id}")
for item in client.dataset(run.default_dataset_id).iterate_items():
    print(item)

# 📚 Want to learn more 📖? Go to → https://docs.apify.com/api/client/python/docs/quick-start

```

## CLI example

```bash
echo '{
  "source": [
    "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF-Binary/DamagedHelmet.glb"
  ]
}' |
apify call sergeyfaraday/glb-to-usdz --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "type": "http",
            "url": "https://mcp.apify.com/?tools=fetch-actor-details,sergeyfaraday/glb-to-usdz"
        }
    }
}

```

The hosted server signs you in with OAuth on first connect, so no API token belongs in this config. Clients without OAuth support can send an `Authorization: Bearer <APIFY_API_TOKEN>` header instead, using a token from API & Integrations in Apify Console (https://console.apify.com/settings/integrations).

## OpenAPI specification

Download the OpenAPI definition: https://api.apify.com/v2/actors/QzihBfpykGvKipwHM/builds/qRAupY2T18fx5G1aD/openapi.json
