Edit a quote's lines and packages
The edit_quote_lines MCP tool: edit a quote's lines and packages.
edit_quote_lines · writes
REST: POST /v1/quotes/{quoteId}/lines
What the model reads
Edits a quote's lines and packages in one call (up to 50 ops, all or nothing): add_line (kind flight, hotel or other; put it in a package with packageId, or make it an upgrade of a base line with replacesItemId + packageId), update_line (only the fields you send change), remove_line (its upgrades go with it), add_package (up to 3, package quotes only), rename_package, remove_package (only when empty). Give an add a clientId to refer to it in later ops of the same call. Lines linked to the trip's design refuse edits to what the design owns (a linked transport's route, dates and times; a linked hotel's city): change the design with update_trip, then sync_quote_with_design. Prices are decimal strings in euros; hotel room prices are per stay; only an 'other' line may be negative (a discount). Read get_quote first for line ids.
Permissions: quotes:write.
Set dryRun: true to preview the effect without writing anything.
Undo: the result names a change id; undo_change reverts it.
Input
| Field | Type | Required | Description |
|---|---|---|---|
quoteId |
uuid | yes | |
ops |
object | object | object | object | object | object[] | yes | max 50 items |
expectedUpdatedAt |
datetime | The quote's updatedAt as you read it; the write is refused (409) if the quote changed since. | |
dryRun |
boolean | Preview only: plan the change and return its effect without writing. |
Input schema (JSON)
{
"type": "object",
"properties": {
"quoteId": {
"type": "string",
"format": "uuid"
},
"ops": {
"type": "array",
"items": {
"anyOf": [
{
"type": "object",
"properties": {
"op": {
"type": "string",
"const": "add_line"
},
"clientId": {
"type": "string",
"pattern": "^[A-Za-z0-9_-]{1,40}$",
"description": "Your own name for what this op creates, so later ops in the same batch can refer to it."
},
"line": {
"anyOf": [
{
"type": "object",
"properties": {
"kind": {
"type": "string",
"const": "flight"
},
"name": {
"type": "string",
"maxLength": 300
},
"bookingRef": {
"type": "string",
"maxLength": 100,
"description": "The booking reference (localizador)."
},
"comments": {
"type": "string",
"maxLength": 4000
},
"marginable": {
"type": "boolean",
"description": "Whether the quote's margin applies to this line (default true)."
},
"catalogRef": {
"anyOf": [
{
"type": "object",
"properties": {
"kind": {
"type": "string",
"minLength": 1,
"maxLength": 40
},
"id": {
"type": "string",
"minLength": 1,
"maxLength": 100
}
},
"required": [
"kind",
"id"
],
"additionalProperties": false
},
{
"type": "null"
}
]
},
"packageId": {
"anyOf": [
{
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
{
"type": "null"
}
],
"description": "Put the line in an upgrade package (package quotes only)."
},
"replacesItemId": {
"anyOf": [
{
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
{
"type": "null"
}
],
"description": "Make the line an upgrade of this base line, inside packageId. Same kind as the base."
},
"role": {
"type": "string",
"enum": [
"ida",
"interno",
"vuelta"
]
},
"mode": {
"type": "string",
"enum": [
"avion",
"tren",
"ferry",
"autobus",
"coche"
]
},
"from": {
"type": "string",
"maxLength": 200
},
"to": {
"type": "string",
"maxLength": 200
},
"date": {
"anyOf": [
{
"type": "string",
"pattern": "^\\d{4}-\\d{2}-\\d{2}$"
},
{
"type": "null"
}
]
},
"departTime": {
"type": "string",
"pattern": "^(?:[01]\\d|2[0-3]):[0-5]\\d$|^$"
},
"arriveTime": {
"type": "string",
"pattern": "^(?:[01]\\d|2[0-3]):[0-5]\\d$|^$"
},
"arriveDayOffset": {
"type": "integer",
"minimum": 0,
"maximum": 14
},
"flight": {
"type": "object",
"properties": {
"flightNo": {
"type": "string",
"maxLength": 12
},
"airline": {
"type": "string",
"maxLength": 8
},
"fromAirport": {
"type": "string",
"maxLength": 8
},
"toAirport": {
"type": "string",
"maxLength": 8
}
},
"additionalProperties": false
},
"price": {
"type": "string",
"pattern": "^-?\\d{1,9}(\\.\\d{1,2})?$"
},
"perPax": {
"type": "boolean"
},
"pairedWithId": {
"anyOf": [
{
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
{
"type": "null"
}
],
"description": "On a return: the outbound flight line that carries the round-trip price."
}
},
"required": [
"kind"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"kind": {
"type": "string",
"const": "hotel"
},
"name": {
"type": "string",
"maxLength": 300
},
"bookingRef": {
"type": "string",
"maxLength": 100,
"description": "The booking reference (localizador)."
},
"comments": {
"type": "string",
"maxLength": 4000
},
"marginable": {
"type": "boolean",
"description": "Whether the quote's margin applies to this line (default true)."
},
"catalogRef": {
"anyOf": [
{
"type": "object",
"properties": {
"kind": {
"type": "string",
"minLength": 1,
"maxLength": 40
},
"id": {
"type": "string",
"minLength": 1,
"maxLength": 100
}
},
"required": [
"kind",
"id"
],
"additionalProperties": false
},
{
"type": "null"
}
]
},
"packageId": {
"anyOf": [
{
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
{
"type": "null"
}
],
"description": "Put the line in an upgrade package (package quotes only)."
},
"replacesItemId": {
"anyOf": [
{
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
{
"type": "null"
}
],
"description": "Make the line an upgrade of this base line, inside packageId. Same kind as the base."
},
"stopId": {
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A stop of the trip's design: the hotel takes the stop's city."
},
"city": {
"type": "string",
"maxLength": 200
},
"nights": {
"type": "integer",
"minimum": 0,
"maximum": 365
},
"board": {
"type": "string",
"maxLength": 200
},
"rooms": {
"type": "array",
"items": {
"type": "object",
"properties": {
"type": {
"type": "string",
"maxLength": 200
},
"qty": {
"type": "integer",
"minimum": 1,
"maximum": 50
},
"price": {
"type": "string",
"pattern": "^-?\\d{1,9}(\\.\\d{1,2})?$",
"description": "Per STAY, not per night."
}
},
"required": [
"type",
"qty",
"price"
],
"additionalProperties": false
},
"minItems": 1,
"maxItems": 20
},
"optionKind": {
"type": "string",
"enum": [
"line",
"hotel"
]
},
"place": {
"type": "object",
"properties": {
"placeId": {
"type": "string",
"maxLength": 300
},
"lat": {
"anyOf": [
{
"type": "number",
"minimum": -90,
"maximum": 90
},
{
"type": "null"
}
]
},
"lng": {
"anyOf": [
{
"type": "number",
"minimum": -180,
"maximum": 180
},
{
"type": "null"
}
]
},
"formattedAddress": {
"type": "string",
"maxLength": 500
}
},
"required": [
"placeId",
"lat",
"lng",
"formattedAddress"
],
"additionalProperties": false
}
},
"required": [
"kind"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"kind": {
"type": "string",
"const": "other"
},
"name": {
"type": "string",
"maxLength": 300
},
"bookingRef": {
"type": "string",
"maxLength": 100,
"description": "The booking reference (localizador)."
},
"comments": {
"type": "string",
"maxLength": 4000
},
"marginable": {
"type": "boolean",
"description": "Whether the quote's margin applies to this line (default true)."
},
"catalogRef": {
"anyOf": [
{
"type": "object",
"properties": {
"kind": {
"type": "string",
"minLength": 1,
"maxLength": 40
},
"id": {
"type": "string",
"minLength": 1,
"maxLength": 100
}
},
"required": [
"kind",
"id"
],
"additionalProperties": false
},
{
"type": "null"
}
]
},
"packageId": {
"anyOf": [
{
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
{
"type": "null"
}
],
"description": "Put the line in an upgrade package (package quotes only)."
},
"replacesItemId": {
"anyOf": [
{
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
{
"type": "null"
}
],
"description": "Make the line an upgrade of this base line, inside packageId. Same kind as the base."
},
"tag": {
"anyOf": [
{
"type": "string",
"enum": [
"actividad",
"traslado",
"seguro"
]
},
{
"type": "null"
}
]
},
"qty": {
"type": "number",
"minimum": 0,
"maximum": 10000
},
"price": {
"type": "string",
"pattern": "^-?\\d{1,9}(\\.\\d{1,2})?$",
"description": "Unit price; negative for a discount."
},
"perPax": {
"type": "boolean"
},
"range": {
"anyOf": [
{
"type": "object",
"properties": {
"start": {
"type": "object",
"properties": {
"offset": {
"type": "integer",
"minimum": 0,
"maximum": 365
},
"time": {
"type": "string",
"pattern": "^(?:[01]\\d|2[0-3]):[0-5]\\d$|^$"
}
},
"required": [
"offset",
"time"
],
"additionalProperties": false
},
"end": {
"type": "object",
"properties": {
"offset": {
"type": "integer",
"minimum": 0,
"maximum": 365
},
"time": {
"type": "string",
"pattern": "^(?:[01]\\d|2[0-3]):[0-5]\\d$|^$"
}
},
"required": [
"offset",
"time"
],
"additionalProperties": false
}
},
"required": [
"start",
"end"
],
"additionalProperties": false
},
{
"type": "null"
}
]
},
"place": {
"type": "object",
"properties": {
"placeId": {
"type": "string",
"maxLength": 300
},
"lat": {
"anyOf": [
{
"type": "number",
"minimum": -90,
"maximum": 90
},
{
"type": "null"
}
]
},
"lng": {
"anyOf": [
{
"type": "number",
"minimum": -180,
"maximum": 180
},
{
"type": "null"
}
]
},
"formattedAddress": {
"type": "string",
"maxLength": 500
}
},
"required": [
"placeId",
"lat",
"lng",
"formattedAddress"
],
"additionalProperties": false
}
},
"required": [
"kind"
],
"additionalProperties": false
}
]
}
},
"required": [
"op",
"line"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"op": {
"type": "string",
"const": "update_line"
},
"id": {
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
"set": {
"type": "object",
"properties": {
"name": {
"type": "string",
"maxLength": 300
},
"bookingRef": {
"type": "string",
"maxLength": 100,
"description": "The booking reference (localizador)."
},
"comments": {
"type": "string",
"maxLength": 4000
},
"marginable": {
"type": "boolean",
"description": "Whether the quote's margin applies to this line (default true)."
},
"catalogRef": {
"anyOf": [
{
"type": "object",
"properties": {
"kind": {
"type": "string",
"minLength": 1,
"maxLength": 40
},
"id": {
"type": "string",
"minLength": 1,
"maxLength": 100
}
},
"required": [
"kind",
"id"
],
"additionalProperties": false
},
{
"type": "null"
}
]
},
"role": {
"type": "string",
"enum": [
"ida",
"interno",
"vuelta"
]
},
"mode": {
"type": "string",
"enum": [
"avion",
"tren",
"ferry",
"autobus",
"coche"
]
},
"from": {
"type": "string",
"maxLength": 200
},
"to": {
"type": "string",
"maxLength": 200
},
"date": {
"anyOf": [
{
"type": "string",
"pattern": "^\\d{4}-\\d{2}-\\d{2}$"
},
{
"type": "null"
}
]
},
"departTime": {
"type": "string",
"pattern": "^(?:[01]\\d|2[0-3]):[0-5]\\d$|^$"
},
"arriveTime": {
"type": "string",
"pattern": "^(?:[01]\\d|2[0-3]):[0-5]\\d$|^$"
},
"arriveDayOffset": {
"type": "integer",
"minimum": 0,
"maximum": 14
},
"flight": {
"type": "object",
"properties": {
"flightNo": {
"type": "string",
"maxLength": 12
},
"airline": {
"type": "string",
"maxLength": 8
},
"fromAirport": {
"type": "string",
"maxLength": 8
},
"toAirport": {
"type": "string",
"maxLength": 8
}
},
"additionalProperties": false
},
"price": {
"type": "string",
"pattern": "^-?\\d{1,9}(\\.\\d{1,2})?$",
"description": "Unit price; negative for a discount."
},
"perPax": {
"type": "boolean"
},
"pairedWithId": {
"anyOf": [
{
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
{
"type": "null"
}
],
"description": "On a return: the outbound flight line that carries the round-trip price."
},
"city": {
"type": "string",
"maxLength": 200
},
"nights": {
"type": "integer",
"minimum": 0,
"maximum": 365
},
"board": {
"type": "string",
"maxLength": 200
},
"rooms": {
"type": "array",
"items": {
"type": "object",
"properties": {
"type": {
"type": "string",
"maxLength": 200
},
"qty": {
"type": "integer",
"minimum": 1,
"maximum": 50
},
"price": {
"type": "string",
"pattern": "^-?\\d{1,9}(\\.\\d{1,2})?$",
"description": "Per STAY, not per night."
}
},
"required": [
"type",
"qty",
"price"
],
"additionalProperties": false
},
"minItems": 1,
"maxItems": 20
},
"optionKind": {
"type": "string",
"enum": [
"line",
"hotel"
]
},
"place": {
"type": "object",
"properties": {
"placeId": {
"type": "string",
"maxLength": 300
},
"lat": {
"anyOf": [
{
"type": "number",
"minimum": -90,
"maximum": 90
},
{
"type": "null"
}
]
},
"lng": {
"anyOf": [
{
"type": "number",
"minimum": -180,
"maximum": 180
},
{
"type": "null"
}
]
},
"formattedAddress": {
"type": "string",
"maxLength": 500
}
},
"required": [
"placeId",
"lat",
"lng",
"formattedAddress"
],
"additionalProperties": false
},
"tag": {
"anyOf": [
{
"type": "string",
"enum": [
"actividad",
"traslado",
"seguro"
]
},
{
"type": "null"
}
]
},
"qty": {
"type": "number",
"minimum": 0,
"maximum": 10000
},
"range": {
"anyOf": [
{
"type": "object",
"properties": {
"start": {
"type": "object",
"properties": {
"offset": {
"type": "integer",
"minimum": 0,
"maximum": 365
},
"time": {
"type": "string",
"pattern": "^(?:[01]\\d|2[0-3]):[0-5]\\d$|^$"
}
},
"required": [
"offset",
"time"
],
"additionalProperties": false
},
"end": {
"type": "object",
"properties": {
"offset": {
"type": "integer",
"minimum": 0,
"maximum": 365
},
"time": {
"type": "string",
"pattern": "^(?:[01]\\d|2[0-3]):[0-5]\\d$|^$"
}
},
"required": [
"offset",
"time"
],
"additionalProperties": false
}
},
"required": [
"start",
"end"
],
"additionalProperties": false
},
{
"type": "null"
}
]
}
},
"additionalProperties": false
}
},
"required": [
"op",
"id",
"set"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"op": {
"type": "string",
"const": "remove_line"
},
"id": {
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
}
},
"required": [
"op",
"id"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"op": {
"type": "string",
"const": "add_package"
},
"clientId": {
"type": "string",
"pattern": "^[A-Za-z0-9_-]{1,40}$",
"description": "Your own name for what this op creates, so later ops in the same batch can refer to it."
},
"name": {
"type": "string",
"minLength": 1,
"maxLength": 60
}
},
"required": [
"op"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"op": {
"type": "string",
"const": "rename_package"
},
"id": {
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
},
"name": {
"type": "string",
"minLength": 1,
"maxLength": 60
}
},
"required": [
"op",
"id",
"name"
],
"additionalProperties": false
},
{
"type": "object",
"properties": {
"op": {
"type": "string",
"const": "remove_package"
},
"id": {
"type": "string",
"minLength": 1,
"maxLength": 64,
"description": "A line or package id from get_quote, or the clientId an earlier op in this batch gave it."
}
},
"required": [
"op",
"id"
],
"additionalProperties": false
}
]
},
"minItems": 1,
"maxItems": 50
},
"expectedUpdatedAt": {
"type": "string",
"format": "date-time",
"description": "The quote's updatedAt as you read it; the write is refused (409) if the quote changed since."
},
"dryRun": {
"type": "boolean",
"description": "Preview only: plan the change and return its effect without writing."
}
},
"required": [
"quoteId",
"ops"
],
"additionalProperties": false
}