Чиптрип-экспедиция «Краски Марокко» — v3
Предложений 1, в эталоне агента 1. Дословных полей нет в посте: 0. Строк с суммой, не взятой ценой: 1 (налог, сноска или пропуск — видно в разделе 3). Отличий от эталона агента: 4 (это не ошибки, а места, где агент и модель прочитали пост по-разному; смотрите оценку Opus)
1 Что подали модели
📋 Промпт — системный, ровно как отправлен модели, со всей разметкой (27225 знаков)
PROMPT + EXAMPLE + FORMAT версии одним текстом. Пост пришёл отдельным сообщением — следующий спойлер.
# Роль
Ты — внимательный редактор турагентства Cheap Trip. Ты читаешь один пост блога с подборкой туров и переносишь из него факты о поездке в JSON. Ты ничего не считаешь, не выбираешь лучшее и не сокращаешь.
# Зачем это нужно
- Покупатель заходит на страницу сайта о стране, городе, острове или пляже и ищет туры туда.
- По твоему ответу программа решит, на каких страницах показать пост и какую цену «от» там написать.
- Пропустишь место — покупатель, который ищет это место, тур не найдёт.
- Пропустишь предложение — на странице может оказаться неверная цена «от».
- Поэтому выписывай **всё**, что есть в посте. Минимальную цену, страницы сайта и адреса считает программа, не ты.
# Что на входе
Сообщение из четырёх разделов:
- `# Заголовок поста`
- `# Дата публикации` — `ГГГГ-ММ-ДД`; по ней определяешь год у дат без года.
- `# Метки блога` — через запятую.
- `# Текст поста` — как его написал редактор.
# Четыре вида полей
| Вид поля | Как узнать | Что писать |
|---|---|---|
| Дословное | имя оканчивается на `_as_in_post` | Скопируй символ в символ из заголовка, меток или текста: тот же падеж, регистр, знаки, пробелы, опечатки. Не пересказывай и не исправляй. Программа проверит, что такая строка есть в посте. |
| Именительный падеж | имя оканчивается на `_nominative` | То же название по-русски в именительном падеже. Родовое слово из поста («Бухта», «Пляж», «Залив», «остров») сохрани, сокращение раскрой: «Москвы» → «Москва», «в Сингапуре» → «Сингапур», «о. Бали» → «остров Бали», «Бухта Санья» → «Бухта Санья». |
| Из закрытого списка | `place_type`, `place_role_in_trip`, `found_in`, `price_is_for`, `price_currency` | Ровно одно значение из списка в формате, слово в слово. Своих формулировок не пиши. |
| Число или дата | `price_amount`, `nights`, `hotel_stars`, `departure_date` | Число без пробелов и знаков; дата `ГГГГ-ММ-ДД`. |
# Порядок работы
Иди по шагам. Каждый шаг — по всему посту, от первой строки до последней.
## Шаг 1. Это предложение тура?
- `post_is_trip_offer: true` — пост предлагает купить тур, подборку отелей, круиз или экспедицию.
- `false` — новость, совет, конкурс, рассказ без тура. Тогда все списки пустые, поля `_as_in_post` — `null`, дальше не иди.
## Шаг 2. Город вылета и перелёт
- `departure_city_as_in_post` — город из фразы вида «Вылет из Москвы» → «Москвы». Его же в именительном — `departure_city_nominative`.
- `flight_included_evidence_as_in_post` — дословный кусок, по которому видно, входит перелёт или нет: строка из «В стоимость тура включено» с авиаперелётом, «с перелетом» из заголовка или «без перелета» из строки цены.
## Шаг 3. Страны
- Каждая страна, где турист живёт или что посещает по программе.
- Не страна поездки: страна пересадки («стыковка в Дохе» — Катар не пиши), страна вылета.
- `found_in` — откуда видно, что страна в поездке: обычно «заголовок» или «метки блога».
## Шаг 4. Места мельче страны
Выпиши **каждое** место мельче страны, которое названо в посте, — и укажи, зачем оно названо (`place_role_in_trip`). Не выбрасывай место из-за роли: выводить ли тур на его страницу, решит программа по роли.
Где искать:
- строки отелей — после значка «•»: «Golden Tulip Media Hotel⭐⭐⭐⭐ • Дубай, Джумейра» — два места;
- заголовок и метки блога;
- программа и маршрут: «Токио (3 ночи) → оз. Кавагутико → Киото», «День 3. Хиросима», «10 ночей на о. Бали», порты круиза;
- «В стоимость тура включено»: «авиаперелет Москва — Бали, Денпасар» — Денпасар — город прилёта;
- описания отелей: «Беспл. трансфер на песчаный пляж Al Khan».
Правила:
- Одно место — одна запись, даже если оно встречается много раз. Но бухта, пляж или остров и город с тем же именем — **разные** места: «Бухта Санья» в строке отеля и город Санья в «перелет Санкт-Петербург — Санья» — две записи, каждая со своим типом и ролью. Бери кусок поста, из которого лучше всего видна роль, — из него копируй `place_name_as_in_post` и его указывай в `found_in`.
- Место отеля важнее остальных ролей: если в месте есть отель, роль — «место отеля».
- Город вылета сюда не пиши — он уже в шаге 2.
- Не места: названия авиакомпаний, ресторанов, офисов Cheap Trip, улицы офиса. Название отеля целиком — не место, но место **внутри** названия отеля («Avani Hotel Deira» → Дейра) выписывается с ролью «в названии отеля».
## Шаг 5. Отели и все их предложения
Отель — строка с названием, обычно со звёздами и местом после разделителя. Оформление бывает разным, смысл один:
- звёзды — значки ⭐⭐⭐⭐ или «4*»; `hotel_stars` — их число;
- место после «•», «—», «-» или «|»;
- цена — «39 261 ₽», «39 261 руб.», «2890 $»;
- строка цены — «15 декабря • 5 ночей — 39 261 ₽» или «Вылет 15 декабря, 5 ночей: 39 261 руб.».
Строка без звёзд — тоже отель, если под ней описание и цены.
Для каждого отеля в порядке поста:
- `hotel_name_as_in_post` — название без ⭐ и без места: «Avani Hotel Deira (ex. Movenpick Hotel Deira)».
- `hotel_stars` — число значков ⭐.
- `hotel_place_names_as_in_post` — каждое место после «•» отдельно.
- `place_names_inside_hotel_name_as_in_post` — район, пляж, город, остров внутри самого названия отеля: «Avani Hotel Deira» → «Deira». Слова «Hotel», «Resort», «Beach», «Village» и названия сетей — не места. Каждое такое место выпиши и в `places` с ролью «в названии отеля», если его нет после «•».
- `hotel_is_fixed_part_of_combined_tour` — `true`, если отель входит в каждое предложение комбинированного тура и своих цен не имеет («В конце отдыха 2 ночи в Сингапуре в отеле»).
- `offers` — **каждая** строка с ценой тура под этим отелем, до строки следующего отеля.
Как читать строку цены «15 декабря • 5 ночей — 39 261 ₽»:
- `departure_date_as_in_post` — кусок с датой целиком, как в посте: «15 декабря», «с 17 по 27 октября». Не собирай дату из частей: «17 октября» в посте «с 17 по 27 октября» не написано;
- `departure_date` — с годом: ближайшая такая дата не раньше даты публикации;
- `nights` — 5; в строке «14 ночей (12 ночей в отелях)» — первое число, 14;
- `price_as_in_post` — «39 261 ₽»; `price_amount` — 39261; `price_currency` — RUB;
- `price_conditions_as_in_post` — ближайшая строка **над** ценой, где сказано, за что цена и какое питание: «С человека при покупке тура на двоих. Завтраки.» Одна строка условий действует на все цены под ней до следующей строки условий или следующего отеля;
- `price_is_for` — смысл строки условий из закрытого списка;
- `room_category_as_in_post` — особая категория номера, за которую дана цена, дословно, только её название: «Клубный люкс (Club Suite, 65 м²)». Обычно она стоит строкой над условиями и действует на все цены под ней. Обычный номер или категория не сказана — `null`;
- `flight_included` — входит ли перелёт в эту цену.
Не предложения тура — не пиши в `offers`:
- топливный сбор, туристический налог, виза, депозит, доплата, скидка, страховка, трансфер, экскурсия за доплату;
- сноски со «*» о стоимости перелёта или других отелей;
- суммы в описании отеля и в разделе «Дополнительно оплачивается».
## Шаг 6. Туры без отелей
Экспедиция, экскурсионный или автобусный тур, круиз, где цена стоит не под отелем, а под датами тура. Каждый такой тур — запись в `tours_without_hotel` с маршрутом и всеми предложениями. Места маршрута выпиши и в `places` с ролью «место по маршруту или программе», включая места в скобках: «Мерзуга (Сахара, 1 ночь)» — Мерзуга и Сахара. Пустыня, гора, озеро — тип «природный объект: гора, озеро, река, лес».
## Шаг 7. Сверка перед ответом
- Посчитай строки с ценой тура в посте и предложения в ответе — числа равны. Если редактор написал «N предложений в M отелях», сверь с этим.
- Каждое место из строк отелей есть в `places`.
- Каждое поле `_as_in_post` скопировано, а не пересказано.
- В каждом поле из закрытого списка — значение из списка.
- Сомневаешься — напиши в `doubts_comment`, в чём и почему, с дословной цитатой. Сомнений нет — пустая строка.
- Сомнение пиши, только если оно может изменить место, отель, цену или дату в ответе. Не пиши о пробелах и знаках, о выборе типа места, пересказ своих решений.
- Не повод для сомнения: «Под запрос», «гарантия», «Тур с 7.10 — под запрос» — это наличие мест в отеле, цена под ними — обычное предложение.
# Ответ
- Один JSON по формату ниже, без пояснений вокруг.
- Ниже — пример на отрывке другого поста и формат ответа с описанием каждого поля.
# Пример
Ниже — **отрывок** другого поста: из 9 отелей оставлены 3, служебные строки сокращены. Ответ на отрывок — полный: в нём всё, что есть в отрывке.
## Вход — отрывок поста
```
# Заголовок поста
Сингапур и Индонезия, о. Бали — от 163 616 ₽ с перелетом
# Дата публикации
2026-09-29
# Метки блога
Без виз, Заграница, Пляжный отдых, На праздники, предложение, Бали, Сингапур, Раннее бронирование, 14 ночей, Экзотика, Индонезия
# Текст поста
Вылет из Москвы 12 февраля на 14 ночей. На День защитника Отечества!
Комбинированные туры:
В конце отдыха 2 ночи в Сингапуре в отеле*:
Ywca Fort Canning (ex. Fort Canning Lodge)⭐⭐⭐⭐ • Сингапур
Под запрос — отель проверит, есть ли место. Возможно, придется искать замену.
* Можно выбрать отели 3⭐ или 5⭐ — стоимость запрашивайте!
ПЛЮС в начале отдыха — 10 ночей на о. Бали в отеле на выбор:
Bakung Sari Resort And Spa⭐⭐⭐ • Кута
Под запрос — отель проверит, есть ли место. 10 мин ходьбы до пляжа, открытый бассейн.
С человека при покупке тура на двоих. Завтраки.
12 февраля • 14 ночей (12 ночей в отелях) — 163 616 ₽
Сингл. Завтраки.
12 февраля • 14 ночей (12 ночей в отелях) — 197 901 ₽
Monolocale Resort Seminyak⭐⭐⭐⭐⭐ • Семиньяк
Tripadvisor: 4,9
С человека при покупке тура на двоих. Завтраки.
12 февраля • 14 ночей (12 ночей в отелях) — 187 761 ₽
В стоимость тура включено:
— авиаперелет Москва — Бали, Денпасар (с удобной короткой стыковкой в Дохе, виза не нужна);
— авиаперелет Сингапур — Москва (с удобной короткой стыковкой в Дохе, виза не нужна);
— внутренний перелет Бали, Денпасар — Сингапур;
— проживание: 10 ночей на о. Бали и 2 ночи в Сингапуре с завтраками в выбранном отеле с указанным питанием;
Дополнительно оплачивается:
— на Бали — обязательный туристический налог (Tourism Promotional Fee) — 150 000 IDR (~10 $, оплачивается на месте);
```
## Что здесь важно
- «Ywca Fort Canning» — отель комбинированного тура: он входит в каждое предложение, своих цен нет → `hotel_is_fixed_part_of_combined_tour: true`, `offers: []`.
- «12 февраля» при публикации 2026-09-29 → `2027-02-12`: 12 февраля 2026 уже прошло.
- «14 ночей (12 ночей в отелях)» → `nights: 14`.
- «Сингл. Завтраки.» → `price_is_for: "одноместное размещение"`, а сама строка — дословно в `price_conditions_as_in_post`.
- «о. Бали» — дословно с «о.», в именительном — «остров Бали»: сокращение раскрыто, родовое слово сохранено.
- Доказательство перелёта — строка «авиаперелет Москва — Бали, Денпасар (…)» из «В стоимость тура включено»; у тура «без перелета» им была бы строка цены с этими словами.
- Денпасар — город прилёта, Доха — пересадка: записаны со своими ролями, а не выброшены. В `place_name_as_in_post` у Дохи — «Дохе», как в посте.
- Катар — страна пересадки, в `countries` его нет.
- «150 000 IDR» — налог, не предложение. Сноска «стоимость запрашивайте» — без цены, не предложение.
- «Ywca Fort Canning» — в названии отеля парк Fort Canning: он в `place_names_inside_hotel_name_as_in_post` и в `places` с ролью «в названии отеля». «Monolocale Resort Seminyak» — Seminyak тоже в поле отеля, но в `places` второй раз не пишется: Семиньяк уже есть как место отеля после «•».
- Категория номера не названа — `room_category_as_in_post: null`.
- Предложений в отрывке 3 — в ответе 3.
## Ответ
```json
{
"post_is_trip_offer": true,
"departure_city_as_in_post": "Москвы",
"departure_city_nominative": "Москва",
"flight_included_evidence_as_in_post": "авиаперелет Москва — Бали, Денпасар (с удобной короткой стыковкой в Дохе, виза не нужна)",
"countries": [
{
"country_name_as_in_post": "Сингапур",
"country_name_nominative": "Сингапур",
"found_in": "заголовок"
},
{
"country_name_as_in_post": "Индонезия",
"country_name_nominative": "Индонезия",
"found_in": "заголовок"
}
],
"places": [
{
"place_name_as_in_post": "Сингапур",
"place_name_nominative": "Сингапур",
"place_type": "город",
"country_name_nominative": "Сингапур",
"place_role_in_trip": "место отеля",
"found_in": "строка отеля"
},
{
"place_name_as_in_post": "Fort Canning",
"place_name_nominative": "Форт-Каннинг",
"place_type": "природный парк или заповедник",
"country_name_nominative": "Сингапур",
"place_role_in_trip": "в названии отеля",
"found_in": "строка отеля"
},
{
"place_name_as_in_post": "о. Бали",
"place_name_nominative": "остров Бали",
"place_type": "остров",
"country_name_nominative": "Индонезия",
"place_role_in_trip": "место отеля",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Кута",
"place_name_nominative": "Кута",
"place_type": "курорт или посёлок",
"country_name_nominative": "Индонезия",
"place_role_in_trip": "место отеля",
"found_in": "строка отеля"
},
{
"place_name_as_in_post": "Семиньяк",
"place_name_nominative": "Семиньяк",
"place_type": "курорт или посёлок",
"country_name_nominative": "Индонезия",
"place_role_in_trip": "место отеля",
"found_in": "строка отеля"
},
{
"place_name_as_in_post": "Денпасар",
"place_name_nominative": "Денпасар",
"place_type": "город",
"country_name_nominative": "Индонезия",
"place_role_in_trip": "город прилёта",
"found_in": "состав тура «В стоимость включено»"
},
{
"place_name_as_in_post": "Дохе",
"place_name_nominative": "Доха",
"place_type": "город",
"country_name_nominative": "Катар",
"place_role_in_trip": "пересадка в пути",
"found_in": "состав тура «В стоимость включено»"
}
],
"hotels": [
{
"hotel_name_as_in_post": "Ywca Fort Canning (ex. Fort Canning Lodge)",
"hotel_stars": 4,
"hotel_place_names_as_in_post": [
"Сингапур"
],
"place_names_inside_hotel_name_as_in_post": [
"Fort Canning"
],
"hotel_is_fixed_part_of_combined_tour": true,
"offers": []
},
{
"hotel_name_as_in_post": "Bakung Sari Resort And Spa",
"hotel_stars": 3,
"hotel_place_names_as_in_post": [
"Кута"
],
"place_names_inside_hotel_name_as_in_post": [],
"hotel_is_fixed_part_of_combined_tour": false,
"offers": [
{"departure_date_as_in_post": "12 февраля", "departure_date": "2027-02-12", "nights": 14, "price_as_in_post": "163 616 ₽", "price_amount": 163616, "price_currency": "RUB", "price_conditions_as_in_post": "С человека при покупке тура на двоих. Завтраки.", "price_is_for": "с человека при покупке на двоих", "room_category_as_in_post": null, "flight_included": true},
{"departure_date_as_in_post": "12 февраля", "departure_date": "2027-02-12", "nights": 14, "price_as_in_post": "197 901 ₽", "price_amount": 197901, "price_currency": "RUB", "price_conditions_as_in_post": "Сингл. Завтраки.", "price_is_for": "одноместное размещение", "room_category_as_in_post": null, "flight_included": true}
]
},
{
"hotel_name_as_in_post": "Monolocale Resort Seminyak",
"hotel_stars": 5,
"hotel_place_names_as_in_post": [
"Семиньяк"
],
"place_names_inside_hotel_name_as_in_post": [
"Seminyak"
],
"hotel_is_fixed_part_of_combined_tour": false,
"offers": [
{"departure_date_as_in_post": "12 февраля", "departure_date": "2027-02-12", "nights": 14, "price_as_in_post": "187 761 ₽", "price_amount": 187761, "price_currency": "RUB", "price_conditions_as_in_post": "С человека при покупке тура на двоих. Завтраки.", "price_is_for": "с человека при покупке на двоих", "room_category_as_in_post": null, "flight_included": true}
]
}
],
"tours_without_hotel": [],
"doubts_comment": "«Можно выбрать отели 3⭐ или 5⭐ — стоимость запрашивайте!» — цены нет, предложением не считаю."
}
```
# Формат ответа — JSON-схема
```json
{
"title": "Поездки из поста — страны, места, отели, предложения с ценами и датами из одного поста блога Cheap Trip",
"type": "object",
"additionalProperties": false,
"required": ["post_is_trip_offer", "departure_city_as_in_post", "departure_city_nominative", "flight_included_evidence_as_in_post", "countries", "places", "hotels", "tours_without_hotel", "doubts_comment"],
"properties": {
"post_is_trip_offer": {
"type": "boolean",
"description": "true — пост предлагает купить тур, подборку отелей, круиз или экспедицию; false — новость, совет, конкурс без тура. При false все списки пустые."
},
"departure_city_as_in_post": {
"type": ["string", "null"],
"description": "Город вылета дословно, как в посте: «Вылет из Москвы» → «Москвы». Не сказан — null."
},
"departure_city_nominative": {
"type": ["string", "null"],
"description": "Город вылета в именительном падеже: «Москва». Не сказан — null."
},
"flight_included_evidence_as_in_post": {
"type": ["string", "null"],
"description": "Дословный кусок поста, по которому видно, входит перелёт или нет: строка из «В стоимость тура включено», «с перелетом» из заголовка или «без перелета» из строки цены. Нет такого куска — null."
},
"countries": {
"type": "array",
"description": "Страны, куда едет турист: где он живёт или что посещает по программе. Страна пересадки и страна вылета сюда не входят.",
"items": {
"type": "object",
"additionalProperties": false,
"required": ["country_name_as_in_post", "country_name_nominative", "found_in"],
"properties": {
"country_name_as_in_post": {"type": "string", "description": "Название страны дословно из поста: «ОАЭ», «Индонезии»."},
"country_name_nominative": {"type": "string", "description": "Название страны в именительном падеже: «ОАЭ», «Индонезия»."},
"found_in": {"$ref": "#/$defs/found_in"}
}
}
},
"places": {
"type": "array",
"description": "Каждое географическое место мельче страны, названное в посте: город, остров, курорт, район, пляж, бухта, город прилёта, пересадка. Одно место — одна запись. Город вылета сюда не входит: он в departure_city_*.",
"items": {
"type": "object",
"additionalProperties": false,
"required": ["place_name_as_in_post", "place_name_nominative", "place_type", "country_name_nominative", "place_role_in_trip", "found_in"],
"properties": {
"place_name_as_in_post": {"type": "string", "description": "Название места дословно из того куска поста, который указан в found_in: «Джумейра», «Сингапуре», «о. Бали», «Al Khan»."},
"place_name_nominative": {"type": "string", "description": "То же место в именительном падеже по-русски. Родовое слово из поста — «Бухта», «Пляж», «Залив», «остров» — сохраняется, сокращение раскрывается: «о. Бали» → «остров Бали», «Бухта Санья» → «Бухта Санья», «в Сингапуре» → «Сингапур». Бухта Санья и город Санья — разные места, у каждого своя запись. Латиницу — в общепринятое русское написание, если оно известно; иначе как в посте."},
"place_type": {"$ref": "#/$defs/place_type"},
"country_name_nominative": {"type": "string", "description": "Страна, в которой находится место, в именительном падеже: «ОАЭ», «Катар»."},
"place_role_in_trip": {"$ref": "#/$defs/place_role_in_trip"},
"found_in": {"$ref": "#/$defs/found_in"}
}
}
},
"hotels": {
"type": "array",
"description": "Каждый отель подборки в порядке поста — и с ценами, и без своих цен.",
"items": {
"type": "object",
"additionalProperties": false,
"required": ["hotel_name_as_in_post", "hotel_stars", "hotel_place_names_as_in_post", "place_names_inside_hotel_name_as_in_post", "hotel_is_fixed_part_of_combined_tour", "offers"],
"properties": {
"hotel_name_as_in_post": {"type": "string", "description": "Название отеля дословно, без звёзд ⭐ и без места после «•»: «Avani Hotel Deira (ex. Movenpick Hotel Deira)»."},
"hotel_stars": {"type": ["integer", "null"], "description": "Число значков ⭐ после названия. Нет значков — null."},
"hotel_place_names_as_in_post": {"type": "array", "items": {"type": "string"}, "description": "Места после «•» в строке отеля, каждое отдельно и дословно: «• Дубай, Джумейра» → [\"Дубай\", \"Джумейра\"]. Места нет — []."},
"place_names_inside_hotel_name_as_in_post": {"type": "array", "items": {"type": "string"}, "description": "Район, пляж, город, остров, который стоит внутри названия отеля, — каждое отдельно и дословно: «Avani Hotel Deira» → [\"Deira\"], «Anantara Mui Ne Resort» → [\"Mui Ne\"]. Слова «Hotel», «Resort», «Beach», «Village», названия сетей — не места. Нет — []."},
"hotel_is_fixed_part_of_combined_tour": {"type": "boolean", "description": "true — отель входит в каждое предложение комбинированного тура и своих цен не имеет («В конце отдыха 2 ночи в Сингапуре в отеле»). Иначе false."},
"offers": {"type": "array", "items": {"$ref": "#/$defs/offer"}, "description": "Все предложения отеля — каждая строка с ценой тура под этим отелем. Своих цен нет — []."}
}
}
},
"tours_without_hotel": {
"type": "array",
"description": "Туры, у которых в посте нет списка отелей с ценами: экспедиции, экскурсионные и автобусные туры, круизы. Нет таких — [].",
"items": {
"type": "object",
"additionalProperties": false,
"required": ["tour_name_as_in_post", "route_place_names_as_in_post", "offers"],
"properties": {
"tour_name_as_in_post": {"type": "string", "description": "Название тура дословно; нет названия — заголовок поста дословно."},
"route_place_names_as_in_post": {"type": "array", "items": {"type": "string"}, "description": "Места маршрута дословно, в порядке маршрута, включая места в скобках: «Токио (3 ночи) → оз. Кавагутико → Киото» → [\"Токио\", \"оз. Кавагутико\", \"Киото\"]; «Мерзуга (Сахара, 1 ночь)» → [\"Мерзуга\", \"Сахара\"]."},
"offers": {"type": "array", "items": {"$ref": "#/$defs/offer"}, "description": "Все предложения тура."}
}
}
},
"doubts_comment": {
"type": "string",
"description": "Одна-две фразы, в чём сомневаешься и почему, с дословной цитатой спорного места. Сомнений нет — пустая строка."
}
},
"$defs": {
"offer": {
"type": "object",
"additionalProperties": false,
"required": ["departure_date_as_in_post", "departure_date", "nights", "price_as_in_post", "price_amount", "price_currency", "price_conditions_as_in_post", "price_is_for", "room_category_as_in_post", "flight_included"],
"properties": {
"departure_date_as_in_post": {"type": ["string", "null"], "description": "Дата вылета дословно, весь кусок с датой как в посте: «15 декабря», «с 17 по 27 октября», «26.09». Не собирай дату из частей. Нет даты — null."},
"departure_date": {"type": ["string", "null"], "description": "Дата вылета ГГГГ-ММ-ДД. Год не написан — ближайшая такая дата не раньше даты публикации: пост 2026-09-29, «12 февраля» → 2027-02-12. Нет даты — null."},
"nights": {"type": ["integer", "null"], "description": "Число ночей тура — первое число ночей в строке цены: «14 ночей (12 ночей в отелях)» → 14. Нет — null."},
"price_as_in_post": {"type": "string", "description": "Цена дословно с валютой: «39 261 ₽», «2890 $»."},
"price_amount": {"type": "integer", "description": "Цена числом без пробелов: 39261."},
"price_currency": {"type": "string", "enum": ["RUB", "USD", "EUR", "другая"], "description": "₽ и руб — RUB, $ — USD, € — EUR."},
"price_conditions_as_in_post": {"type": ["string", "null"], "description": "Строка условий цены дословно — ближайшая строка над ценой, где сказано, за что цена и какое питание: «С человека при покупке тура на двоих. Завтраки.», «Сингл. Завтраки.». Нет такой строки — null."},
"price_is_for": {"$ref": "#/$defs/price_is_for"},
"room_category_as_in_post": {"type": ["string", "null"], "description": "Особая категория номера, за которую дана цена, дословно: «Клубный люкс (Club Suite, 65 м²)», «Вилла с собственным бассейном (One Bedroom Pool Villa, 200 м²)». Только название категории, без перечня удобств после двоеточия. Обычный номер или категория не сказана — null."},
"flight_included": {"type": ["boolean", "null"], "description": "true — перелёт входит в цену («с перелетом» в заголовке, перелёт в «В стоимость тура включено»); false — «без перелета» в строке цены или посте; null — в посте не сказано."}
}
},
"price_is_for": {
"type": "string",
"enum": ["с человека при покупке на двоих", "одноместное размещение", "с человека, размещение не сказано", "за номер", "другое", "не сказано"],
"description": "За что цена — по смыслу строки условий. «С человека при покупке тура на двоих», «Место в двухместном номере» → «с человека при покупке на двоих»; «Одноместное размещение», «Сингл» → «одноместное размещение»; «на 1 человека», «с человека» без слов о размещении (экспедиции, экскурсионные туры) → «с человека, размещение не сказано»; «за номер», «за виллу» → «за номер»; строки условий нет → «не сказано»."
},
"place_type": {
"type": "string",
"enum": ["регион или провинция", "город", "курорт или посёлок", "район", "остров", "полуостров", "атолл или архипелаг", "бухта или залив", "пляж", "природный парк или заповедник", "природный объект: гора, озеро, река, лес", "другой объект: дорога, здание, место"],
"description": "Тип места — список типов из справочника мест 110 без «страны»: страны пишутся в countries."
},
"place_role_in_trip": {
"type": "string",
"enum": ["место отеля", "место по маршруту или программе", "город прилёта", "пересадка в пути", "в названии отеля", "упомянуто в описании отеля", "только в заголовке или метках", "за доплату"],
"description": "Зачем место названо в посте. «место отеля» — место из строки отеля подборки или место, где стоит отель; «только в заголовке или метках» — ставить, только если в тексте поста места нет совсем; «место по маршруту или программе» — турист туда едет по программе тура; «город прилёта» — аэропорт или город, куда прилетает самолёт тура, а отелей там нет; «пересадка в пути» — стыковка, транзит; «в названии отеля» — район или пляж виден только в названии отеля («Avani Hotel Deira» → Дейра), после «•» его нет; «упомянуто в описании отеля» — пляж, парк, центр рядом с отелем, трансфер туда; «за доплату» — экскурсия или поездка за отдельные деньги."
},
"found_in": {
"type": "string",
"enum": ["заголовок", "метки блога", "строка отеля", "описание отеля", "маршрут или программа тура", "состав тура «В стоимость включено»", "другой текст поста"],
"description": "Кусок поста, из которого видна роль места и из которого скопировано дословное название."
}
}
}
```
📝 Пост — ровно та часть, которую модель читала как пост
Сообщение пользователя целиком. Адрес, номер поста и блог модели не показывались.
# Заголовок поста Чиптрип-экспедиция «Краски Марокко» # Дата публикации 2026-09-02 # Метки блога 10 ночей, Юнеско, Заграница, столица, Авторский тур, people-to-go, Без виз, предложение, Марокко, Спецпроект Ч, чиптрип экспедиция # Текст поста Невероятное путешествие в одну из самых красивых и аутентичных стран Северной Африки! Photo by Carlos Leret on Unsplash Спецпроект Ч Привет, я Оксана, редактор Чиптрип. Приглашаю вас в великолепное Королевство Марокко по маршруту: Касабланка → Рабат (1 ночь) → Шефшауэн (1 ночь) → Фес (2 ночи) → Мерзуга (Сахара, 1 ночь) → Варзазат (1 ночь) → Айт-Бен-Хадду → Марракеш (2 ночи) → Эссуэйра (2 ночи) → Касабланка Это страна тысячи красок, в существование которых так трудно верится, но когда вы увидите это собственными глазами, то удивитесь. Во время путешествия нам предстоит: попробовать национальные марокканские блюда — тажин и кускус, любоваться красотой мавританских дворцов и садов в вечно вибрирующем Марракеше, жить в сказочных риадах, залезть на португальские бастионы и объесться свежей рыбой и морепродуктами в Эссуэйре. А еще — увидеть, как обрабатывают кожу точно так же, как и сто лет назад, восхититься размерами медины Феса, пить много мятного чая и свежевыжатого апельсинового сока всегда и везде, отправиться в Сахару и провести там ночь, посмотреть закат в пустыне и прокатиться на верблюдах по песчаным барханам. И, наконец, мы побываем в Касабланке, прогуляемся по знаменитому синему городу Шефшауэну, накупим всего-всего на рынках и полюбим Марокко за его бесконечное разнообразие! Язык общения — русский! Сопровождать экспедицию будет опытный адепт Чиптрипа + будут экскурсии с местными гидами. Даты экспедиции: с 17 по 27 октября Стоимость на 10 ночей на 1 человека: 1859 € — без перелета* * Стоимость перелета Москва — Касабланка — Москва от 750 €, стоимость дана ориентировочная, актуальные цены уточняйте при бронировании! ❗️ Забронировать экспедицию удаленно: ✉️ Почта — cheaptripexpedition@gmail.com ПРОГРАММУ ЭКСПЕДИЦИИ ПОДРОБНО И ЧТО ВКЛЮЧЕНО ▶ СМОТРИ ЗДЕСЬ ◀
🧭 Как устроен вызов
claude -p ▶️ один вызов на пост, один ответ ├── --system-prompt 📋 PROMPT + EXAMPLE + FORMAT одним текстом — одинаково для всех постов ├── сообщение пользователя 📝 пост: # Заголовок поста / # Дата публикации / # Метки блога / # Текст поста └── --json-schema 🔒 та же схема ещё раз: Claude Code проверяет по ней форму ответа
2 Что вернула модель
Перелёт, доказательство: «1859 € — без перелета*»
Страны
| Как в посте | Именительный | Где найдено |
|---|---|---|
| Марокко | Марокко | заголовок |
Места
| Как в посте | Именительный | Тип | Страна | Роль в поездке | Где найдено |
|---|---|---|---|---|---|
| Касабланка | Касабланка | город | Марокко | место по маршруту или программе | маршрут или программа тура |
| Рабат | Рабат | город | Марокко | место по маршруту или программе | маршрут или программа тура |
| Шефшауэн | Шефшауэн | город | Марокко | место по маршруту или программе | маршрут или программа тура |
| Фес | Фес | город | Марокко | место по маршруту или программе | маршрут или программа тура |
| Мерзуга | Мерзуга | курорт или посёлок | Марокко | место по маршруту или программе | маршрут или программа тура |
| Сахара | Сахара | природный объект: гора, озеро, река, лес | Марокко | место по маршруту или программе | маршрут или программа тура |
| Варзазат | Варзазат | город | Марокко | место по маршруту или программе | маршрут или программа тура |
| Айт-Бен-Хадду | Айт-Бен-Хадду | курорт или посёлок | Марокко | место по маршруту или программе | маршрут или программа тура |
| Марракеш | Марракеш | город | Марокко | место по маршруту или программе | маршрут или программа тура |
| Эссуэйра | Эссуэйра | город | Марокко | место по маршруту или программе | маршрут или программа тура |
Тур без отелей: Чиптрип-экспедиция «Краски Марокко»
Маршрут: Касабланка → Рабат → Шефшауэн → Фес → Мерзуга → Сахара → Варзазат → Айт-Бен-Хадду → Марракеш → Эссуэйра → Касабланка
| Дата в посте | Дата | Ночей | Цена в посте | Сумма | Валюта | Условия цены в посте | За что цена | Категория номера | Перелёт |
|---|---|---|---|---|---|---|---|---|---|
| с 17 по 27 октября | 2026-10-17 | 10 | 1859 € | 1859 | EUR | Стоимость на 10 ночей на 1 человека: | с человека, размещение не сказано | — | нет |
Сомнения модели: —
🧩 Ответ как JSON, только симпатично
Ровно поля и значения ответа модели (часть answer), без пересказа: слева имя поля, справа значение; "строка", число, true / false, null. Карточка — объект, номер — место в списке; списки сворачиваются. Наведите на имя поля — описание и закрытый список из формата v3.
список, элементов: 1
список, элементов: 10
список, элементов: 1
список, элементов: 1
Исходные данные — JSON, как вернула модель
{
"run": {
"prompt_version": "v3",
"prompt_folder": "trip-places-hotels-prices-llm/prompt-v3",
"post_folder": "trip-places-hotels-prices-llm/posts-one-folder-per-post/2026-09-02__msk__46316286",
"model": "claude-haiku-5-5",
"effort": "medium",
"finished_at": "2026-10-09T09:03:44Z",
"duration_seconds": 16.3,
"input_tokens_full_price": 2,
"input_tokens_cache_read": 0,
"input_tokens_cache_write": 19076,
"output_tokens": 3907,
"conditional_price_usd_if_it_were_api": 0.0057689
},
"answer": {
"post_is_trip_offer": true,
"departure_city_as_in_post": "Москва",
"departure_city_nominative": "Москва",
"flight_included_evidence_as_in_post": "1859 € — без перелета*",
"countries": [
{
"country_name_as_in_post": "Марокко",
"country_name_nominative": "Марокко",
"found_in": "заголовок"
}
],
"places": [
{
"place_name_as_in_post": "Касабланка",
"place_name_nominative": "Касабланка",
"place_type": "город",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Рабат",
"place_name_nominative": "Рабат",
"place_type": "город",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Шефшауэн",
"place_name_nominative": "Шефшауэн",
"place_type": "город",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Фес",
"place_name_nominative": "Фес",
"place_type": "город",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Мерзуга",
"place_name_nominative": "Мерзуга",
"place_type": "курорт или посёлок",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Сахара",
"place_name_nominative": "Сахара",
"place_type": "природный объект: гора, озеро, река, лес",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Варзазат",
"place_name_nominative": "Варзазат",
"place_type": "город",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Айт-Бен-Хадду",
"place_name_nominative": "Айт-Бен-Хадду",
"place_type": "курорт или посёлок",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Марракеш",
"place_name_nominative": "Марракеш",
"place_type": "город",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
},
{
"place_name_as_in_post": "Эссуэйра",
"place_name_nominative": "Эссуэйра",
"place_type": "город",
"country_name_nominative": "Марокко",
"place_role_in_trip": "место по маршруту или программе",
"found_in": "маршрут или программа тура"
}
],
"hotels": [],
"tours_without_hotel": [
{
"tour_name_as_in_post": "Чиптрип-экспедиция «Краски Марокко»",
"route_place_names_as_in_post": [
"Касабланка",
"Рабат",
"Шефшауэн",
"Фес",
"Мерзуга",
"Сахара",
"Варзазат",
"Айт-Бен-Хадду",
"Марракеш",
"Эссуэйра",
"Касабланка"
],
"offers": [
{
"departure_date_as_in_post": "с 17 по 27 октября",
"departure_date": "2026-10-17",
"nights": 10,
"price_as_in_post": "1859 €",
"price_amount": 1859,
"price_currency": "EUR",
"price_conditions_as_in_post": "Стоимость на 10 ночей на 1 человека:",
"price_is_for": "с человека, размещение не сказано",
"room_category_as_in_post": null,
"flight_included": false
}
]
}
],
"doubts_comment": ""
}
}3 Где в посте то, что выписано
Подсветка: город вылета перелёт: доказательство страна место отель дата вылета условия цены цена сумма не взята ценой — наведите на подсветку, чтобы увидеть поля ответа.
# Заголовок поста
Чиптрип-экспедиция «Краски Марокко»
# Дата публикации
2026-09-02
# Метки блога
10 ночей, Юнеско, Заграница, столица, Авторский тур, people-to-go, Без виз, предложение, Марокко, Спецпроект Ч, чиптрип экспедиция
# Текст поста
Невероятное путешествие в одну из самых красивых и аутентичных стран Северной Африки!
Photo by Carlos Leret on Unsplash
Спецпроект Ч
Привет, я Оксана, редактор Чиптрип.
Приглашаю вас в великолепное Королевство Марокко по маршруту: Касабланка → Рабат (1 ночь) → Шефшауэн (1 ночь) → Фес (2 ночи) → Мерзуга (Сахара, 1 ночь) → Варзазат (1 ночь) → Айт-Бен-Хадду → Марракеш (2 ночи) → Эссуэйра (2 ночи) → Касабланка
Это страна тысячи красок, в существование которых так трудно верится, но когда вы увидите это собственными глазами, то удивитесь.
Во время путешествия нам предстоит: попробовать национальные марокканские блюда — тажин и кускус, любоваться красотой мавританских дворцов и садов в вечно вибрирующем Марракеше, жить в сказочных риадах, залезть на португальские бастионы и объесться свежей рыбой и морепродуктами в Эссуэйре.
А еще — увидеть, как обрабатывают кожу точно так же, как и сто лет назад, восхититься размерами медины Феса, пить много мятного чая и свежевыжатого апельсинового сока всегда и везде, отправиться в Сахару и провести там ночь, посмотреть закат в пустыне и прокатиться на верблюдах по песчаным барханам.
И, наконец, мы побываем в Касабланке, прогуляемся по знаменитому синему городу Шефшауэну, накупим всего-всего на рынках и полюбим Марокко за его бесконечное разнообразие!
Язык общения — русский! Сопровождать экспедицию будет опытный адепт Чиптрипа + будут экскурсии с местными гидами.
Даты экспедиции: с 17 по 27 октября
Стоимость на 10 ночей на 1 человека:
1859 € — без перелета*
* Стоимость перелета Москва — Касабланка — Москва от 750 €, стоимость дана ориентировочная, актуальные цены уточняйте при бронировании!
❗️ Забронировать экспедицию удаленно:
✉️ Почта — cheaptripexpedition@gmail.com
ПРОГРАММУ ЭКСПЕДИЦИИ ПОДРОБНО И ЧТО ВКЛЮЧЕНО ▶ СМОТРИ ЗДЕСЬ ◀
4 Проверки
⚖️ Оценка независимого Claude Opus — главная: справилась ли модель и что заденет покупателя
🔎 Скрипт вхождений: все ли дословные поля ответа есть в посте — не выдумала ли модель
📐 Отличия от эталона агента — вспомогательно
Эталон — ответ, который до прогона написал по тому же промпту агент Claude, прочитав пост вручную. Модели он не показывается. Отличие — не обязательно ошибка: в спорных местах агент и модель часто выбирают разные допустимые прочтения (тип места, роль, где найдено). Ошибки определяет оценка Opus выше; эта таблица помогает быстро найти, где смотреть.
| Поле | В ответе модели | В эталоне агента |
|---|---|---|
| departure_city_as_in_post | "Москва" | null |
| departure_city_nominative | "Москва" | null |
| flight_included_evidence_as_in_post | "1859 € — без перелета*" | "1859 € — без перелета" |
| tours_without_hotel[0].tour_name_as_in_post | "Чиптрип-экспедиция «Краски Марокко»" | "Краски Марокко" |
Файл эталона: EXPECTED-answer-format-v3-written-by-agent-before-run-not-shown-to-haiku.json