run_id and access_token) raises the allowance. Nothing is personalised to the scan.
- Fuzzy matches below 0.8 confidence are returned as
matched: false, so invented or misspelled names aren’t reported as a real ingredient. - An unmatched entry means only that Skan didn’t recognise the text. It says nothing about whether the ingredient is safe or approved.
invalid_input, catalog_unavailable, rate_limited.
| Tool | analyze_ingredients |
| Listed on | /mcp (guest) and /mcp/account (OAuth) |
| Annotations | readOnlyHint: false destructiveHint: false openWorldHint: true |
Input
Sent asparams.arguments of tools/call. Unknown keys are rejected with invalid_input.
string
Optional: the person’s scan, which raises the free allowance.Format
uuid.string
Pattern
^[a-f0-9]{64}$.string | string[]
required
Max length 6000. Max 50 items.
Output
Returned asstructuredContent, and as the same object serialised in content[0].text. On failure the result has isError: true and an error body instead.
object[]
required
Max 50 items.
Show item
Show item
string
required
boolean
required
number
required
Range 0–1.
enum<string> | null
required
One of
exact_name, exact_alternative, fuzzy_name, fuzzy_alternative.string | null
required
string | null
required
string[]
required
Max 8 items.
string[]
required
Max 8 items.
string[]
required
Max 8 items.
string[]
required
Max 4 items.
string | null
required
object
required
object
required
string
required
string
required
Description the model receives
Description the model receives
Look up a skincare product's ingredient list in Skan's ingredient database and return what each matched ingredient is and what it is commonly used for. Send the label text, or up to 50 individual names. An unmatched entry means only that Skan did not recognise the text; never present it as unknown, unsafe or unapproved. Check entitlement.upgrade_required before you describe the result: when it is true the free allowance is spent and `items` is empty for that reason, so say the allowance is used up and point the person at the Skan app — do not tell them Skan recognised none of their ingredients, and do not start a scan to reset it. This is cosmetic reference information, not medical advice, not a safety assessment, and not a judgement about a specific person's skin. Completes in one call; it is not a background job.
Input JSON Schema
Input JSON Schema
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"type": "object",
"properties": {
"run_id": {
"description": "Optional: the person's scan, which raises the free allowance.",
"type": "string",
"format": "uuid",
"pattern": "^([0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[1-8][0-9a-fA-F]{3}-[89abAB][0-9a-fA-F]{3}-[0-9a-fA-F]{12}|00000000-0000-0000-0000-000000000000|ffffffff-ffff-ffff-ffff-ffffffffffff)$"
},
"access_token": {
"type": "string",
"pattern": "^[a-f0-9]{64}$"
},
"ingredients": {
"anyOf": [
{
"type": "string",
"maxLength": 6000,
"description": "A product's ingredient list as printed on the label. Must not be empty."
},
{
"maxItems": 50,
"type": "array",
"items": {
"type": "string",
"maxLength": 120
},
"description": "Individual ingredient names. At least one, at most 50."
}
]
}
},
"required": [
"ingredients"
],
"additionalProperties": false
}
Output JSON Schema
Output JSON Schema
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"type": "object",
"properties": {
"items": {
"maxItems": 50,
"type": "array",
"items": {
"type": "object",
"properties": {
"input_text": {
"type": "string"
},
"matched": {
"type": "boolean"
},
"match_confidence": {
"type": "number",
"minimum": 0,
"maximum": 1
},
"match_type": {
"anyOf": [
{
"type": "string",
"enum": [
"exact_name",
"exact_alternative",
"fuzzy_name",
"fuzzy_alternative"
]
},
{
"type": "null"
}
]
},
"name": {
"type": [
"string",
"null"
]
},
"description": {
"type": [
"string",
"null"
]
},
"what_it_does": {
"maxItems": 8,
"type": "array",
"items": {
"type": "string"
}
},
"benefits": {
"maxItems": 8,
"type": "array",
"items": {
"type": "string"
}
},
"concerns": {
"maxItems": 8,
"type": "array",
"items": {
"type": "string"
}
},
"ingredient_type": {
"maxItems": 4,
"type": "array",
"items": {
"type": "string"
}
},
"suitable_for_time": {
"type": [
"string",
"null"
]
}
},
"required": [
"input_text",
"matched",
"match_confidence",
"match_type",
"name",
"description",
"what_it_does",
"benefits",
"concerns",
"ingredient_type",
"suitable_for_time"
],
"additionalProperties": false
}
},
"summary": {
"type": "object",
"properties": {
"total": {
"type": "integer",
"minimum": 0,
"maximum": 9007199254740991
},
"matched": {
"type": "integer",
"minimum": 0,
"maximum": 9007199254740991
},
"unmatched": {
"type": "integer",
"minimum": 0,
"maximum": 9007199254740991
}
},
"required": [
"total",
"matched",
"unmatched"
],
"additionalProperties": false
},
"entitlement": {
"type": "object",
"properties": {
"tier": {
"type": "string",
"const": "free_guest"
},
"used": {
"type": "integer",
"minimum": 0,
"maximum": 9007199254740991
},
"included": {
"type": "integer",
"minimum": 0,
"maximum": 9007199254740991
},
"remaining": {
"type": "integer",
"minimum": 0,
"maximum": 9007199254740991
},
"upgrade_required": {
"type": "boolean"
},
"more_in_app": {
"type": "string"
}
},
"required": [
"tier",
"used",
"included",
"remaining",
"upgrade_required",
"more_in_app"
],
"additionalProperties": false
},
"unmatched_meaning": {
"type": "string"
},
"limitations": {
"type": "string"
}
},
"required": [
"items",
"summary",
"entitlement",
"unmatched_meaning",
"limitations"
],
"additionalProperties": false
}
{
"jsonrpc": "2.0", "id": 6, "method": "tools/call",
"params": {
"name": "analyze_ingredients",
"arguments": { "ingredients": ["Niacinamide", "Xyzzyl Glowamide"] }
}
}
{
"items": [
{
"input_text": "Niacinamide",
"matched": true,
"match_confidence": 1,
"match_type": "exact_name",
"name": "Niacinamide",
"description": "Niacinamide, a potent form of vitamin B3, is celebrated for its wide-ranging benefits in skincare. …",
"what_it_does": ["Smoothing"],
"benefits": ["Anti-Aging", "Soothing", "Fades Dark Spots", "Controls Oil Production", "Pore Minimizer", "Brightening"],
"concerns": [],
"ingredient_type": ["Antioxidant", "Humectant", "Niacinamide"],
"suitable_for_time": "both"
},
{
"input_text": "Xyzzyl Glowamide",
"matched": false,
"match_confidence": 0.56,
"match_type": null,
"name": null,
"description": null,
"what_it_does": [],
"benefits": [],
"concerns": [],
"ingredient_type": [],
"suitable_for_time": null
}
],
"summary": { "total": 2, "matched": 1, "unmatched": 1 },
"entitlement": { "tier": "free_guest", "used": 1, "included": 5, "remaining": 4, "upgrade_required": false, "more_in_app": "…" },
"unmatched_meaning": "An unmatched entry means only that Skan's ingredient database did not recognise that text. …",
"limitations": "Cosmetic and informational only. This is not medical advice, not a diagnosis, and not a safety assessment. …"
}