feat(masters): add direct masters adimages add - #676
Conversation
|
@claude @codex review PR #676 at exact head f4d4736 (round 99949e75-f57b-4cd9-a7e1-3e556ffb532c). Focus on critical issues: bugs, security vulnerabilities, logical errors, data loss risks, performance problems. Do NOT nitpick style, naming conventions, minor formatting, or subjective preferences — only flag issues that could break functionality or cause real harm in production. |
|
Claude finished @axisrow's task in 3m 35s —— View job Claude review —
|
|
Codex Review: Didn't find any major issues. Swish! Reviewed commit: ℹ️ About Codex in GitHubYour team has set up Codex to review pull requests in this repo. Reviews are triggered when you
If Codex has suggestions, it will comment; otherwise it will react with 👍. Codex can also answer questions or update the PR. Try commenting "@codex address that feedback". |
b17713e to
9d4bf59
Compare
f4d4736 to
fd0ac00
Compare
`masters update --image "N=path"` (#672) can only REPLACE an image that already exists, and refuses outright when a campaign has none. There is no way to add an image beyond the current set, or to put the first one on a campaign that has zero. Adds the append half of the mutating side: direct masters adimages add 72349978 --image-file a.png --image-file b.png Refuses if the current count plus the new files would exceed Yandex's cap of 5. Works from an empty set — images are optional on a Мастер кампаний campaign, exactly like ad images on a text ad via the API. Accepts `--launch` (same draft-publishing semantics as `masters update`). `_apply_image_operations` is the new bulk primitive this is built on: open the image manager modal ONCE, apply every removal and every upload, click Save once. It takes both a removal list and an upload list even though `add` only ever passes uploads — the removal path is what makes it a primitive rather than an `add`-shaped helper, and it is exercised by its own tests here. Removals are located by thumb URLs captured before any removal, so a later removal in the same batch is not thrown off by the panel re-indexing as earlier cards disappear. Uploads poll an ABSOLUTE expected panel size rather than `_set_image`'s relative "grew back to the original size" check, which only happens to work for an exact 1-for-1 swap. Nothing commits before the single Save, so any earlier failure leaves the saved set untouched. `_set_image` — what `update --image` uses — is untouched. `_save_and_verify_images` wraps the shared post-save tail: draft-aware button label, click, verify against an absolute expected end state (via `_verify_image_set_mismatches` from the preceding commit), and translate a mid-verification session expiry into a "do NOT retry" error — uploads are not idempotent, so `_with_session`'s auto-retry must not re-run them. Classified DANGEROUS: no sandbox equivalent exists for Мастер кампаний, real files are uploaded, and a retried `add` appends again. Confirmed live 2026-08-03 on DRAFT campaign 713234191, including uploading into a genuinely empty set. Refs #648 Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
fd0ac00 to
4e9c8d4
Compare
masters update --image "N=path"(#672) умеет только ЗАМЕНИТЬ уже существующее изображение и отказывается работать, когда у кампании их нет. Добавить изображение сверх текущего набора или поставить первое на кампанию с нулём — невозможно.Добавляет дописывающую половину мутирующей стороны:
Отказывается, если текущее количество плюс новые файлы превысят лимит Яндекса в 5. Работает от пустого набора — изображения на кампании МК опциональны, ровно как ad images у текстового объявления через API. Принимает
--launch(та же семантика публикации черновика, что уmasters update)._apply_image_operations— новый bulk-примитив, на котором это построено: открыть модалку менеджера изображений ОДИН раз, применить все удаления и все загрузки, нажать «Сохранить» один раз. Он принимает и список удалений, и список загрузок, хотяaddвсегда передаёт только загрузки — путь удаления и делает его примитивом, а не хелпером формыadd, и покрыт собственными тестами здесь же. Удаления адресуются по thumb URL, снятым ДО первого удаления, чтобы более позднее удаление в том же батче не сбилось из-за переиндексации панели по мере исчезновения ранних карточек. Загрузки опрашивают АБСОЛЮТНЫЙ ожидаемый размер панели, а не относительную проверку_set_image«вырос обратно до исходного размера», которая работает лишь для точного обмена 1-в-1. До единственного «Сохранить» ничего не коммитится, поэтому любой более ранний сбой оставляет сохранённый набор нетронутым._set_image— то, что используетupdate --image— не тронут._save_and_verify_imagesоборачивает общий послесохраняющий хвост: label кнопки с учётом черновика, клик, проверка против абсолютного ожидаемого конечного состояния (через_verify_image_set_mismatchesиз предыдущего PR) и трансляция истёкшей посреди верификации сессии в ошибку «НЕ повторять» — загрузки не идемпотентны, поэтому авторетрай_with_sessionне должен их переигрывать.Классифицировано DANGEROUS: песочницы для Мастера кампаний не существует, загружаются реальные файлы, а повторённый
addдопишет ещё раз.Живая проверка 2026-08-03 на DRAFT-кампании 713234191, включая загрузку в заведомо пустой набор.
Refs #648
🤖 Generated with Claude Code