# PBR channel packing with texture audit (ORM, Unity mask) (`ernestx/pbr-channel-packer`) Actor

Pack PBR maps into glTF/Unreal ORM or Unity mask maps, with an audit of the set: value ranges, roughness/smoothness consistency, normal-map normalization, resolution mismatches, per-channel provenance. Data maps written raw, never colour-managed. PNG or EXR out.

- **URL**: https://apify.com/ernestx/pbr-channel-packer.md
- **Developed by:** [Jean-Baptiste Couche](https://apify.com/ernestx) (community)
- **Categories:** AI, Automation, Developer tools
- **Stats:** 2 total users, 1 monthly users, 100.0% runs succeeded, 0 bookmarks
- **User rating**: No ratings yet

## Pricing

from $50.00 / 1,000 pack completeds

This Actor is paid per event. You are not charged for the Apify platform usage, but only a fixed price for specific events.

Learn more: https://docs.apify.com/platform/actors/running/actors-in-store#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.

In JavaScript/TypeScript projects, use official [JavaScript/TypeScript client](https://docs.apify.com/api/client/js/docs.md):

```bash
npm install apify-client
```

In Python projects, use official [Python client library](https://docs.apify.com/api/client/python/docs.md):

```bash
pip install apify-client
```

In shell scripts, use [Apify CLI](https://docs.apify.com/cli/docs.md):

````bash
# MacOS / Linux
curl -fsSL https://apify.com/install-cli.sh | bash
# Windows
irm https://apify.com/install-cli.ps1 | iex
```bash

In AI frameworks, you might use the [Apify MCP server](https://docs.apify.com/integrations/mcp.md).

If your project is in a different language, use 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

## Pack PBR maps the way the engine actually wants them

Give it your texture maps — separate grayscales, or a glTF-style packed
metallicRoughness — and get back one correctly packed file for your target:
glTF/Unreal ORM, Unity HDRP/URP mask map, or Unity Built-in MetallicGlossMap.
Plus an audit of the set, because the values being in the right channels is
only half the job.

Headless Blender 4.5 LTS image I/O underneath (EXR included), no UI, no
login, callable by agents over MCP.

### The two inversions that ruin texture sets

**Roughness vs smoothness.** Unity stores *smoothness* where everyone else
stores *roughness*. Both Unity layouts here write `A = 1 − roughness` —
inverted exactly once, never twice — and if you supply a genuine smoothness
map it's used as-is. Supply both and they get audited against each other:
if `smoothness ≠ 1 − roughness` beyond tolerance, they describe two
different surfaces and the report says which percentage of texels disagree.

**OpenGL vs DirectX normals.** glTF, Unity and Blender put +Y in the green
channel; Unreal puts −Y. The flip is exact (`G' = 1 − G`, zero
renormalization needed) but the source convention *cannot* be detected from
pixels — so it is never guessed. You declare the direction, the converted
map ships alongside the packed texture, and the report records your
declaration with a plain warning: flip an already-correct map and bumps
become dents.

### Data maps are written raw — and the build proves it

An ORM must never pass through colour management: a gamma curve applied to
a roughness channel is invisible in a viewer and wrong in every render.
This Actor's Docker build writes known pixel values through the exact
production code path, reads them back, and **fails the build** if they come
back off by more than 8-bit quantization. That guard has already caught one
real corruption — Blender silently sRGB-encoding float buffers saved to
PNG — before any customer could hit it.

Output PNG is lossless 8-bit; EXR is float and bit-exact. JPEG is
deliberately refused: chroma subsampling averages neighbouring texels
*across channels that mean different things*.

### The audit

Every run reports, per channel and per source map:

- **Provenance** — `roughness ← G channel of metalRough.jpg`. Traceable,
  not magic. Defaulted channels (no AO supplied → neutral white) are
  declared loudly, never silent.
- **Value statistics** — min/max/mean, % pure black, % pure white. Metallic
  is physically near-binary, so a metallic map living in midtones gets
  flagged: it's usually a spec/gloss map that landed in the wrong slot.
- **Normal map normalization** — decoded vector lengths, p95 deviation from
  unit. Catches maps damaged by resizing or colour management upstream.
- **Resolution handling** — mismatched sources are resampled to the working
  resolution and each resize is reported; NPOT sizes get a warning.
- **An engine import checklist** — the settings that silently undo correct
  files: sRGB flag, Unreal's Masks compression preset, which slot, which
  normal convention the engine expects. In the report, next to the file it
  applies to.

### Input

| Field | Notes |
|---|---|
| `roughnessUrl` / `smoothnessUrl` / `metalRoughUrl` | At least one required — the Actor refuses to invent roughness |
| `occlusionUrl` | Optional; defaults to neutral white, reported |
| `metallicUrl` | Optional; defaults to dielectric 0, reported |
| `normalUrl` | Optional; audited, and converted if `normalConvert` is set |
| `convention` | `gltf-orm`, `unreal-orm`, `unity-mask`, `unity-metallic` |
| `normalConvert` | `none`, `opengl-to-directx`, `directx-to-opengl` |
| `metalRoughHasOcclusion` | For pipelines whose packed source already carries AO in R |
| `resolution` | 0 = largest source; otherwise 4–8192, square |
| `outputFormat` | `png` or `exr` |

### Output

The packed map under `OUTPUT` in the run's key-value store — a ZIP when a
converted normal ships alongside. The dataset record carries the full
report; the unabridged copy lives under `REPORT_FULL`. The packed file is a
data map in Non-Color space: sample it linear, never sRGB — the checklist
in the report says exactly where that switch lives in your engine.

### Verified against

Real assets, end to end on Apify: DamagedHelmet's AO + packed
metallicRoughness recombined into a true 2048² ORM with per-channel
provenance; the same set to a Unity mask map with an OpenGL→DirectX normal
conversion shipping alongside; and the reject path (no roughness source →
explicit `NO_ROUGHNESS_SOURCE`-class refusal, nothing charged).

### Limits worth knowing

Colorspace of *input* files is assumed, not read — image formats carry no
reliable metadata, so values are copied verbatim (the correct handling for
data maps) and the assumption is stated in the report. Channel packing
trusts your labels: it cannot detect that a file named roughness is actually
gloss — though the value statistics often expose it. High→low baking
(normal/AO from a source mesh) is the next tool in this suite, not this one.

# Actor input Schema

## `convention` (type: `string`):

gltf-orm and unreal-orm write R=occlusion, G=roughness, B=metallic. The two Unity layouts store SMOOTHNESS in alpha (computed as 1-roughness unless a smoothness map is supplied - inverted exactly once, never twice): unity-mask is the HDRP/URP mask map, unity-metallic the Built-in Standard MetallicGlossMap. Every output ships with an engine import checklist (sRGB off, compression preset, slot).
## `roughnessUrl` (type: `string`):

Grayscale roughness. At least one of roughnessUrl, smoothnessUrl or metalRoughUrl is required - the Actor refuses to invent roughness.
## `smoothnessUrl` (type: `string`):

Grayscale smoothness/gloss; converted as roughness = 1 - smoothness. If both roughness and smoothness are supplied, their consistency is audited.
## `metalRoughUrl` (type: `string`):

A glTF metallicRoughness texture: G channel = roughness, B channel = metallic. Typical when re-packing an existing glTF asset with a separate AO map.
## `occlusionUrl` (type: `string`):

Grayscale AO. Defaults to neutral white if omitted (reported, never silent).
## `metallicUrl` (type: `string`):

Grayscale metallic. Defaults to 0 (dielectric) if omitted and no metalRough source is given.
## `normalUrl` (type: `string`):

Optional. Not packed into the output - audited instead: vector normalization statistics catch maps damaged by resizing or colour management upstream.
## `normalConvert` (type: `string`):

glTF, Unity and Blender use OpenGL normals (green = Y up); Unreal uses DirectX (green = Y down). The flip (G' = 1-G) is exact and needs no renormalization, but the SOURCE convention cannot be detected from pixels - you declare it, the converted map is emitted alongside the packed texture, and the report records your declaration. Flipping an already-correct map breaks it: bumps become dents.
## `metalRoughHasOcclusion` (type: `boolean`):

Some pipelines ship a full ORM as 'metallicRoughness'. If enabled and no separate AO map is given, the R channel of metalRoughUrl is used as occlusion.
## `resolution` (type: `integer`):

Square output size in pixels, 4..8192. 0 = use the largest source resolution. Sources at other sizes are resampled (reported).
## `outputFormat` (type: `string`):

PNG (8-bit, lossless) or EXR (float, lossless). JPEG is deliberately not offered: chroma subsampling corrupts independently-meaningful channels.

## Actor input object example

```json
{
  "convention": "gltf-orm",
  "metalRoughUrl": "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF/Default_metalRoughness.jpg",
  "occlusionUrl": "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF/Default_AO.jpg",
  "normalConvert": "none",
  "metalRoughHasOcclusion": false,
  "resolution": 0,
  "outputFormat": "png"
}
````

# Actor output Schema

## `packedTexture` (type: `string`):

The packed map under key OUTPUT (PNG or EXR; ZIP if several files). Data map in Non-Color space - sample it linear, never sRGB.

## `auditReport` (type: `string`):

Per-channel provenance, value-range statistics, roughness/smoothness consistency, normal-map normalization, resolution handling.

## `runInConsole` (type: `string`):

No description

# 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 = {
    "metalRoughUrl": "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF/Default_metalRoughness.jpg",
    "occlusionUrl": "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF/Default_AO.jpg"
};

// Run the Actor and wait for it to finish
const run = await client.actor("ernestx/pbr-channel-packer").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 = {
    "metalRoughUrl": "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF/Default_metalRoughness.jpg",
    "occlusionUrl": "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF/Default_AO.jpg",
}

# Run the Actor and wait for it to finish
run = client.actor("ernestx/pbr-channel-packer").call(run_input=run_input)

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

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

```

## CLI example

```bash
echo '{
  "metalRoughUrl": "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF/Default_metalRoughness.jpg",
  "occlusionUrl": "https://raw.githubusercontent.com/KhronosGroup/glTF-Sample-Assets/main/Models/DamagedHelmet/glTF/Default_AO.jpg"
}' |
apify call ernestx/pbr-channel-packer --silent --output-dataset

```

## MCP server setup

```json
{
    "mcpServers": {
        "apify": {
            "command": "npx",
            "args": [
                "mcp-remote",
                "https://mcp.apify.com/?tools=ernestx/pbr-channel-packer",
                "--header",
                "Authorization: Bearer <YOUR_API_TOKEN>"
            ]
        }
    }
}

```

## OpenAPI specification

```json
{
    "openapi": "3.0.1",
    "info": {
        "title": "PBR channel packing with texture audit (ORM, Unity mask)",
        "description": "Pack PBR maps into glTF/Unreal ORM or Unity mask maps, with an audit of the set: value ranges, roughness/smoothness consistency, normal-map normalization, resolution mismatches, per-channel provenance. Data maps written raw, never colour-managed. PNG or EXR out.",
        "version": "0.1",
        "x-build-id": "jfjarGyVy0F2lRea4"
    },
    "servers": [
        {
            "url": "https://api.apify.com/v2"
        }
    ],
    "paths": {
        "/acts/ernestx~pbr-channel-packer/run-sync-get-dataset-items": {
            "post": {
                "operationId": "run-sync-get-dataset-items-ernestx-pbr-channel-packer",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor, waits for its completion, and returns Actor's dataset items in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK"
                    }
                }
            }
        },
        "/acts/ernestx~pbr-channel-packer/runs": {
            "post": {
                "operationId": "runs-sync-ernestx-pbr-channel-packer",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor and returns information about the initiated run in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK",
                        "content": {
                            "application/json": {
                                "schema": {
                                    "$ref": "#/components/schemas/runsResponseSchema"
                                }
                            }
                        }
                    }
                }
            }
        },
        "/acts/ernestx~pbr-channel-packer/run-sync": {
            "post": {
                "operationId": "run-sync-ernestx-pbr-channel-packer",
                "x-openai-isConsequential": false,
                "summary": "Executes an Actor, waits for completion, and returns the OUTPUT from Key-value store in response.",
                "tags": [
                    "Run Actor"
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "$ref": "#/components/schemas/inputSchema"
                            }
                        }
                    }
                },
                "parameters": [
                    {
                        "name": "token",
                        "in": "query",
                        "required": true,
                        "schema": {
                            "type": "string"
                        },
                        "description": "Enter your Apify token here"
                    }
                ],
                "responses": {
                    "200": {
                        "description": "OK"
                    }
                }
            }
        }
    },
    "components": {
        "schemas": {
            "inputSchema": {
                "type": "object",
                "properties": {
                    "convention": {
                        "title": "Target convention",
                        "enum": [
                            "gltf-orm",
                            "unreal-orm",
                            "unity-mask",
                            "unity-metallic"
                        ],
                        "type": "string",
                        "description": "gltf-orm and unreal-orm write R=occlusion, G=roughness, B=metallic. The two Unity layouts store SMOOTHNESS in alpha (computed as 1-roughness unless a smoothness map is supplied - inverted exactly once, never twice): unity-mask is the HDRP/URP mask map, unity-metallic the Built-in Standard MetallicGlossMap. Every output ships with an engine import checklist (sRGB off, compression preset, slot).",
                        "default": "gltf-orm"
                    },
                    "roughnessUrl": {
                        "title": "Roughness map URL",
                        "type": "string",
                        "description": "Grayscale roughness. At least one of roughnessUrl, smoothnessUrl or metalRoughUrl is required - the Actor refuses to invent roughness."
                    },
                    "smoothnessUrl": {
                        "title": "Smoothness (gloss) map URL",
                        "type": "string",
                        "description": "Grayscale smoothness/gloss; converted as roughness = 1 - smoothness. If both roughness and smoothness are supplied, their consistency is audited."
                    },
                    "metalRoughUrl": {
                        "title": "Packed metallicRoughness URL (glTF style)",
                        "type": "string",
                        "description": "A glTF metallicRoughness texture: G channel = roughness, B channel = metallic. Typical when re-packing an existing glTF asset with a separate AO map."
                    },
                    "occlusionUrl": {
                        "title": "Ambient occlusion map URL",
                        "type": "string",
                        "description": "Grayscale AO. Defaults to neutral white if omitted (reported, never silent)."
                    },
                    "metallicUrl": {
                        "title": "Metallic map URL",
                        "type": "string",
                        "description": "Grayscale metallic. Defaults to 0 (dielectric) if omitted and no metalRough source is given."
                    },
                    "normalUrl": {
                        "title": "Normal map URL (audit only)",
                        "type": "string",
                        "description": "Optional. Not packed into the output - audited instead: vector normalization statistics catch maps damaged by resizing or colour management upstream."
                    },
                    "normalConvert": {
                        "title": "Normal map convention conversion",
                        "enum": [
                            "none",
                            "opengl-to-directx",
                            "directx-to-opengl"
                        ],
                        "type": "string",
                        "description": "glTF, Unity and Blender use OpenGL normals (green = Y up); Unreal uses DirectX (green = Y down). The flip (G' = 1-G) is exact and needs no renormalization, but the SOURCE convention cannot be detected from pixels - you declare it, the converted map is emitted alongside the packed texture, and the report records your declaration. Flipping an already-correct map breaks it: bumps become dents.",
                        "default": "none"
                    },
                    "metalRoughHasOcclusion": {
                        "title": "Packed source already carries AO in R",
                        "type": "boolean",
                        "description": "Some pipelines ship a full ORM as 'metallicRoughness'. If enabled and no separate AO map is given, the R channel of metalRoughUrl is used as occlusion.",
                        "default": false
                    },
                    "resolution": {
                        "title": "Output resolution",
                        "minimum": 0,
                        "maximum": 8192,
                        "type": "integer",
                        "description": "Square output size in pixels, 4..8192. 0 = use the largest source resolution. Sources at other sizes are resampled (reported).",
                        "default": 0
                    },
                    "outputFormat": {
                        "title": "Output format",
                        "enum": [
                            "png",
                            "exr"
                        ],
                        "type": "string",
                        "description": "PNG (8-bit, lossless) or EXR (float, lossless). JPEG is deliberately not offered: chroma subsampling corrupts independently-meaningful channels.",
                        "default": "png"
                    }
                }
            },
            "runsResponseSchema": {
                "type": "object",
                "properties": {
                    "data": {
                        "type": "object",
                        "properties": {
                            "id": {
                                "type": "string"
                            },
                            "actId": {
                                "type": "string"
                            },
                            "userId": {
                                "type": "string"
                            },
                            "startedAt": {
                                "type": "string",
                                "format": "date-time",
                                "example": "2025-01-08T00:00:00.000Z"
                            },
                            "finishedAt": {
                                "type": "string",
                                "format": "date-time",
                                "example": "2025-01-08T00:00:00.000Z"
                            },
                            "status": {
                                "type": "string",
                                "example": "READY"
                            },
                            "meta": {
                                "type": "object",
                                "properties": {
                                    "origin": {
                                        "type": "string",
                                        "example": "API"
                                    },
                                    "userAgent": {
                                        "type": "string"
                                    }
                                }
                            },
                            "stats": {
                                "type": "object",
                                "properties": {
                                    "inputBodyLen": {
                                        "type": "integer",
                                        "example": 2000
                                    },
                                    "rebootCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "restartCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "resurrectCount": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "computeUnits": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            },
                            "options": {
                                "type": "object",
                                "properties": {
                                    "build": {
                                        "type": "string",
                                        "example": "latest"
                                    },
                                    "timeoutSecs": {
                                        "type": "integer",
                                        "example": 300
                                    },
                                    "memoryMbytes": {
                                        "type": "integer",
                                        "example": 1024
                                    },
                                    "diskMbytes": {
                                        "type": "integer",
                                        "example": 2048
                                    }
                                }
                            },
                            "buildId": {
                                "type": "string"
                            },
                            "defaultKeyValueStoreId": {
                                "type": "string"
                            },
                            "defaultDatasetId": {
                                "type": "string"
                            },
                            "defaultRequestQueueId": {
                                "type": "string"
                            },
                            "buildNumber": {
                                "type": "string",
                                "example": "1.0.0"
                            },
                            "containerUrl": {
                                "type": "string"
                            },
                            "usage": {
                                "type": "object",
                                "properties": {
                                    "ACTOR_COMPUTE_UNITS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_WRITES": {
                                        "type": "integer",
                                        "example": 1
                                    },
                                    "KEY_VALUE_STORE_LISTS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_INTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_EXTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_SERPS": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            },
                            "usageTotalUsd": {
                                "type": "number",
                                "example": 0.00005
                            },
                            "usageUsd": {
                                "type": "object",
                                "properties": {
                                    "ACTOR_COMPUTE_UNITS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATASET_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "KEY_VALUE_STORE_WRITES": {
                                        "type": "number",
                                        "example": 0.00005
                                    },
                                    "KEY_VALUE_STORE_LISTS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_READS": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "REQUEST_QUEUE_WRITES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_INTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "DATA_TRANSFER_EXTERNAL_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_RESIDENTIAL_TRANSFER_GBYTES": {
                                        "type": "integer",
                                        "example": 0
                                    },
                                    "PROXY_SERPS": {
                                        "type": "integer",
                                        "example": 0
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
    }
}
```
