---
title: "List lenses and stacks"
method: GET
path: "/v1/modules"
tags: ["Discovery"]
---

# List lenses and stacks

`GET /v1/modules`

## Request

- Base URL: `https://api.phototology.com`
- URL: `https://api.phototology.com/v1/modules`
- Auth: HTTP bearer

Returns all available lenses (single analysis dimensions) and curated stacks (pre-bundled lenses for specific domains/use-cases). Use lens names in the `modules`, `modulesAdd`, or `modulesRemove` fields of the analyze request. Use stack names in the `preset` field. Users can combine lenses with a curated stack via `modulesAdd`/`modulesRemove`, or build a custom stack from scratch by passing `modules` directly.

**Naming note.** The API surface uses the wire field names `modules` (individual lenses) and `presets` (curated stacks) for backward compatibility with existing SDK callers. The MCP server exposes the same units as **lenses** and **stacks**. The concept words are lens / stack; the wire field names are `modules` / `preset` and stay that way.

## Response `200`

Available lenses and curated stacks.

- object
  - `modules` object[], required: Individual analysis lenses. Each lens adds specific fields to the analysis output and a default tabular projection.
    - `name` string, required: Module identifier. Use this in the `modules` array.
    - `description` string, required: What this module analyzes
    - `category` string, required: Module category
    - `outputFields` string[], required: Fields this module adds to the `output` object
    - `billable` boolean, required: Whether running this lens charges a credit. `moderation` is the only non-billable lens (always-on safety, always free). Cache hits cost zero credits regardless of `billable`.
    - `defaultColumns` object[], required: Default spreadsheet columns this lens produces when projected to a tabular export. Used by analyze.phototology.com and any SDK/MCP consumer that wants a default tabular projection without re-implementing the mapping.
      - `label` string, required: User-visible spreadsheet column header.
      - `jsonPath` string, required: Dotted path into `analysisResult` for this column's value.
      - `format` 'string' | 'number' | 'date' | 'percentage' | 'tags' | 'hex' | 'count': Cell rendering hint for the export pipeline.
    - `internal` true: `true` if the lens is real (emits output, has columns) but NOT directly selectable via `modules: []` on /v1/analyze. Reachable only through a curated stack (e.g. `vehicle-condition` is reachable via the `vehicle-condition` stack). Omitted for the 15 directly-selectable lenses.
  - `presets` object[], required: Curated stacks: pre-bundled lenses for specific domains and use-cases.
    - `name` string, required: Stack identifier (the curated bundle name). Use this in the `preset` field of the analyze request.
    - `description` string, required: What this curated stack is designed for
    - `modules` string[], required: Lenses included in this curated stack

## Other responses

- `401`: Missing or invalid API key.

---

[API](https://skmtc.dev/phototology/apis/phototology-api.md) · [All operations](https://skmtc.dev/phototology/apis/phototology-api/llms.txt) · [OpenAPI document](https://skmtc.dev/phototology/apis/phototology-api/revisions/3cb0fc707b63?raw)
