Веб-приложение для доставки воды: правила паузы и переноса, смена адреса, реестр клиентов и календарь поставок, плюс базовый планировщик маршрутов.

Доставка воды держится не на разовых заказах, а на повторяемости. Клиенты ждут воду по привычному графику, и сбои чаще всего возникают там, где этот график меняется: переносы, пропуски, паузы, смена адреса, замена контактного лица.
Обычно ломается простая цепочка: оператор пообещал, курьер не увидел, клиент ждал, а к вечеру никто не понимает, где случилась ошибка. Типичные симптомы: пропуски "потому что не заметили", переносы "потому что записали в чат", забытые подъезды и домофоны, маршруты собираются вручную и каждый раз по-разному.
В сервисе почти всегда есть три роли, и у каждой своя "правда":
Для первого релиза не нужно пытаться охватить все. Минимум, который реально наводит порядок, это единый реестр клиентов и календарь поставок с понятными статусами. Маршрутизация может быть простой, но должна быть привязана к конкретным доставкам на конкретный день.
Данные, которые стоит хранить сразу, чтобы не упереться через месяц: клиент (ФИО или компания, телефон), список адресов (с пометками домофон, этаж, время), подписка (периодичность, объем, предпочтения), отдельные поставки (дата, адрес на эту поставку, окно времени) и статус (запланировано, перенесено, пропущено, выполнено, не удалось).
Небольшой пример: клиент "Ирина, офис" получает 2 бутыли по понедельникам. В четверг она просит доставить на другой адрес только на следующую неделю. Если вы храните только "адрес клиента", курьер в понедельник уедет не туда. Если адрес задается на уровне конкретной поставки, ошибка не случится.
Когда этот каркас понятен, веб-приложение для доставки воды проще всего собирать по шагам: сначала роли и статусы, потом таблицы реестра и календаря, и уже после этого - планировщик маршрутов.
Подписка в доставке воды - это правило, по которому клиент получает воду регулярно. В ней фиксируются периодичность (например, раз в неделю), объем (2 бутыли по 19 л), удобные дни (вторник и пятница) и временное окно (например, 9:00-12:00). Это не конкретный заказ на дату, а шаблон, из которого потом появляются поставки.
Ключевое правило: разделяйте подписку и поставку (заказ на дату). Подписка отвечает на вопрос "как обычно?". Поставка отвечает на вопрос "что именно везем 23 января и куда?". Если смешать эти понятия, начнутся типовые ошибки: перенос одной доставки внезапно меняет весь график, а смена адреса "на один раз" превращается в "навсегда".
График поставок удобно хранить как список будущих дат, созданных на основе подписки (например, на 4-8 недель вперед). Тогда диспетчер видит реальную картину, может переносить отдельные доставки и не ломает правило подписки.
Чтобы всем было понятно, держите короткие статусы подписки:
Операции должны быть "безопасными": перенос даты меняет только одну поставку, пропуск отменяет одну поставку, но не трогает остальной график. А смена адреса должна явно иметь режим: "только на эту доставку" или "для всех будущих". Такая модель без конфликтов ложится в веб-приложение для доставки воды и потом не мешает ни маршрутам, ни учету.
Пример: у Ольги подписка по средам. На следующей неделе она уезжает - диспетчер ставит паузу на 10 дней, и поставки на этот период не появляются. А если Ольга просит перенести ближайшую доставку с 24 на 25 число, меняется только один заказ на дату, без переписывания подписки.
Чтобы подписки не превращались в ручной хаос, выделите три отдельные операции: пауза (остановить подписку), пропуск (пропустить одну поставку) и перенос (сдвинуть конкретную поставку). Тогда оператор всегда выбирает понятное действие, а система ведет себя предсказуемо.
Пауза действует с указанной даты (и, при желании, с времени). Важно заранее решить, что делать с уже созданными поставками в будущем. Практичный вариант: все поставки с даты паузы помечаются как "отменены из-за паузы", но остаются в истории.
Возобновление лучше поддержать двумя способами: "с даты" (продолжить по обычному шаблону) или "со следующей возможной доставки" (если пропущен целый период). При возобновлении система заново создает будущие поставки по графику, не трогая фактически выполненные.
Пропуск не останавливает подписку. Он применяется к конкретной дате в календаре поставок и фиксирует причину (клиент уехал, нет тары, ремонт в офисе). Пропущенная поставка остается в расписании как запись со статусом "пропуск", чтобы курьер и диспетчер не спорили, была она или нет.
Перенос относится к конкретной поставке и меняет дату (иногда и временное окно). Полезно поддержать два режима: перенос на ближайшую доступную дату или на выбранную вручную. Ограничения задайте заранее: например, перенос не может увести доставку на дату раньше текущего дня и не должен пересекаться с уже существующей доставкой в тот же адрес и интервал.
Чтобы не обещать лишнего, введите дедлайны изменений:
Отдельно продумайте историю: кто изменил, когда, что было "до" и "после", и почему. Это удобно хранить как журнал событий (пауза, возобновление, пропуск, перенос) и показывать в карточке клиента и в поставке. Если собираете это через чат, сразу закладывайте статусы и журнал действий - иначе потом будет трудно разбирать спорные случаи.
Адреса - место, где подписки чаще всего начинают путаться. У одного клиента может быть дом, офис, дача и еще разовый адрес (например, для подарка). Поэтому удобно хранить у клиента один основной адрес и несколько дополнительных, а каждую конкретную доставку привязывать к выбранному адресу.
Разделите два действия, которые звучат одинаково для клиента: "перенесите мне на другой адрес".
Практичное правило: если клиент говорит "только в этот раз" - меняем адрес у конкретной доставки. Если говорит "теперь всегда сюда" - меняем основной адрес подписки, но не трогаем уже выполненные доставки и не переписываем историю.
Чтобы оператор не ошибся, в интерфейсе лучше показывать два переключателя: "Изменить только эту доставку" и "Изменить адрес подписки". Рядом - короткое пояснение, что будет с будущими датами.
Адрес - это не только улица и дом. В карточке адреса храните поля, которые реально нужны в день доставки: район или зона доставки (для расчета цены и доступных дней), подъезд, этаж, код домофона, наличие лифта и комментарий для курьера. Если контакт на месте отличается от владельца подписки, это тоже лучше фиксировать прямо в адресе.
После смены адреса сразу проверяйте зону: обслуживается ли район, подходит ли день и временное окно, не изменится ли стоимость. Если зона другая, лучше предложить ближайший доступный слот, чем "оставить как было".
Если вы делаете веб-приложение для доставки воды, заведите простое правило валидации: адрес можно сохранить, только если выбранная зона доставки активна.
В день доставки важны скорость и единая версия правды. Рабочий сценарий такой: оператор меняет адрес у конкретной доставки, система фиксирует время и автора изменения, курьер получает обновление и подтверждает, что увидел его.
Пример: клиент в 9:30 пишет, что сегодня будет в офисе, а не дома. Оператор открывает доставку на сегодня, выбирает "изменить только эту доставку", ставит адрес "Офис" и добавляет комментарий "вход со двора". Курьер видит обновление до выезда и не едет по старому адресу.
Реестр клиентов - это ваша "память": кому, куда и на каких условиях вы возите воду. Если он неудобный, операторы начинают вести заметки в мессенджерах, а курьеры ездят "по привычке", и ошибки быстро копятся. В хорошем реестре человек находится за 10 секунд, и сразу видно, что будет дальше по графику.
Начните с простого, но достаточного набора. Важно не только "как связаться", но и то, что влияет на доставку:
Отдельное поле "источник" (рекомендация, реклама, повторный клиент) помогает понять, откуда реально приходят заказы.
Один хороший фильтр заменяет десяток уточнений по телефону. Обычно полезны срезы по району или улице, по статусу подписки, по ближайшей доставке (сегодня/завтра), а также "есть долг" или "переплата".
По ролям часто достаточно двух уровней доступа:
Календарь поставок - экран, где видно работу сервиса по дням: сколько доставок запланировано, в какие окна времени и по каким районам они распределены. Для диспетчера это главный инструмент: он думает не "по подпискам", а "что едет завтра утром и кто это повезет".
Чтобы календарь был полезным, в каждой доставке держите минимум полей: дата и временное окно, клиент и адрес (с привязкой к району), состав заказа (количество бутылей, тара, доптовары), статус (запланировано, подтверждено, выполнено, отменено) и комментарий для курьера.
Автогенерация обычно строится "из подписок на неделю вперед". Раз в день (или по кнопке) система берет активные подписки, применяет правила паузы, пропуска и переноса и создает конкретные доставки на ближайшие 7 дней. Важно: после генерации подписка не исчезает, меняется только календарь. Так проще править реальный план, не ломая базовые условия клиента.
Ручные правки неизбежны, поэтому нужны быстрые действия прямо в календаре: добавить разовую доставку, отменить одну доставку, перенести на другой день или окно, дописать комментарий. Хорошая практика - сохранять причину ("клиент уехал", "не дозвонились") и автора изменения. Эти мелочи потом экономят часы разборов.
Контроль конфликтов нужен сразу, даже в первой версии:
Пример: в среду у клиента Петрова подписка на утро, но он просит перенести на пятницу вечер. Диспетчер открывает доставку в календаре, меняет дату и окно, добавляет комментарий "после 18:00". Система показывает предупреждение: в пятницу вечер уже есть доставка на тот же адрес. Дальше диспетчер решает - объединить в одну поставку или оставить две.
Планировщик маршрутов курьеров не обязан сразу искать "идеальный" путь. На старте важнее, чтобы диспетчер быстро собирал понятный маршрут, а курьер мог ехать без сюрпризов. Практичный минимум: разбить заказы по районам, учесть ограничения (время, вместимость, склад), а затем выстроить простой порядок точек.
Чтобы построение было предсказуемым, заранее договоритесь, что считается "правдой" в данных:
Дальше цель простая: распределить точки по зонам (район, микрорайон, "левый берег/правый берег"), а внутри зоны упорядочить по близости и по окнам времени. Уже это дает заметный эффект без сложной математики.
Хороший результат маршрута - не обязательно карта, а четкий план действий: список остановок по порядку, комментарии (домофон, "оставить у охраны", "нужна сдача"), плюс суммарный план по времени: выезд со склада, ожидания, ориентировочное прибытие к каждому адресу.
Пример: утром 18 доставок. Вы делите их на 2 района и 2 машины, проверяете, что каждая машина по вместимости проходит (например, 12 и 14 бутылей), и получаете два списка остановок с расчетом времени в пути и по 7 минут на точку.
Изменения после построения неизбежны: перенос, новая заявка, отмена. Минимальная логика такая: маршрут "замораживается" после выезда, а новые точки добавляются как вставка в ближайшее подходящее место, где не ломаются окно времени и вместимость. Если не помещается, заявка уходит в "хвост" или на другую машину, а диспетчер видит причину.
Понедельник, у вас 30 клиентов, и веб-приложение для доставки воды уже ведет подписки. Из них 6 клиентов поставили неделю на паузу (ничего не везем и не списываем), 3 попросили пропуск одной доставки (подписка активна, но конкретный визит не едет), еще у двоих - перенос: один со среды на четверг, второй с пятницы на субботу. И вдобавок один клиент в понедельник в 8:40 меняет адрес доставки на сегодня.
Оператор открывает календарь поставок и правит все точечно, не ломая весь график. Важный принцип - меняется не подписка целиком, а конкретные доставки:
После этого оператор нажимает "пересобрать маршрут" на день. Если утром поменяли адрес, система просто пересчитает остановки для одного курьера: точка переместится, а остальные 29 клиентов останутся на местах.
Курьер видит задание списком остановок с окнами времени, адресом, количеством бутылей и комментарием (например, "код домофона"). По каждой остановке он отмечает результат: доставлено, закрыто (никого нет дома), не дозвонились, перенос по инициативе клиента, отказ.
Если "закрыто" или "не дозвонились", оператору приходит причина, и он решает: перенести на завтра или оформить пропуск. На следующую неделю это влияет предсказуемо: перенос добавляет дополнительную доставку, пропуск уменьшает количество визитов, пауза сдвигает график. А "недоставку" можно автоматически предлагать перенести, чтобы подписка не расползалась по датам.
Частая причина провала в том, что команда пытается сделать идеальный сервис сразу. Для первого релиза веб-приложение для доставки воды должно уверенно закрывать базовые вопросы: кто, куда, когда и сколько, плюс простые правки без путаницы.
Ошибки, которые почти всегда всплывают в первые недели, и что делать вместо этого:
Для маршрутов полезно зафиксировать простые нормы и не спорить с ними каждый день:
Практичный подход для старта: собрать минимальную версию в режиме планирования, добавлять правила по фактам и держать возможность отката, чтобы не бояться массовых правок.
Перед запуском важнее всего проверить не "красоту интерфейса", а то, что данные не разваливаются в реальных ситуациях. Лучше потратить один день на проверки, чем потом вручную разруливать десятки звонков и переносов.
Начните с самой маленькой единицы системы - поставки. Откройте 10-20 поставок из разных сценариев (обычная, после переноса, после смены адреса, после паузы) и убедитесь, что карточка читается одним взглядом.
Проверьте базовый минимум:
Затем проверьте связку "реестр клиентов - календарь - маршрут". Быстрый тест: возьмите одного клиента, сделайте паузу на неделю, перенесите одну доставку на другой день и смените адрес на один раз. После этого откройте календарь поставок и маршрут курьера на нужную дату: изменения должны отразиться ровно там, где вы ожидаете, без дублей и пропаж.
Быстрее всего перейти от идеи к работающему сервису помогает короткий, понятный список требований. Он нужен не "для отчета", а чтобы команда одинаково понимала, что считать готовым.
Соберите требования в одном месте: какие сущности есть в системе (клиент, адрес, подписка, поставка, перенос), какие у них статусы (активна, на паузе, пропущена, перенесена), какие дедлайны важны (до какого времени можно менять доставку на завтра) и кто что делает (оператор, логист, курьер, админ).
Дальше разумно собрать прототип через чат, чтобы сразу увидеть скелет продукта. В TakProsto это удобно делать итерациями: описываете поведение словами, затем уточняете детали на примерах.
Практичный порядок, который обычно дает результат за 1-2 дня:
Тестируйте не "в целом", а на жизненном сценарии. Например: клиент перенес доставку с четверга на субботу, в пятницу поставил паузу на 2 недели, а потом сменил адрес только на одну доставку. Если после этого календарь, реестр и маршрутный лист показывают одно и то же, вы близки к рабочей версии.
Если вы собираете такую систему на TakProsto, удобно начинать с режима планирования, а позже при необходимости выгрузить исходный код и продолжить развитие в своем темпе. Платформа доступна на takprosto.ai.
Разделяйте два уровня: подписка хранит правило «как обычно» (дни, объем, окно, предпочтения), а поставка — конкретную доставку на дату с точным адресом и статусом. Тогда переносы, разовые адреса и пропуски не ломают весь график.
Потому что перенос одной доставки часто случайно меняет «шаблон» на будущее, если подписка и поставка смешаны. Правильный вариант — переносить именно поставку на нужную дату, а подписку оставлять как есть.
Сделайте это явным выбором в интерфейсе: «изменить только эту доставку» или «изменить адрес подписки с даты». По умолчанию безопаснее менять адрес только у одной поставки, чтобы случайно не отправить курьера «навсегда» на временный адрес.
Пауза останавливает подписку на период, и поставки в этом окне не должны ехать, но их лучше оставить в истории с понятной причиной. Возобновление удобнее поддержать «с даты» или «со следующей возможной доставки», чтобы график восстановился предсказуемо.
Пропуск — это статус у конкретной поставки на дату: подписка остается активной, а один визит отмечается как «пропущен» с причиной. Так курьер и оператор видят, что это не ошибка и не «забыли», а осознанное решение.
Держите короткий набор, который понимают все: запланировано, перенесено, пропущено, выполнено, не удалось. Чем меньше статусов, тем меньше спорных трактовок, а детали лучше фиксировать комментарием и причиной.
Если адрес хранится только на уровне клиента, курьер поедет по «старому» адресу, даже если изменение было разовым. Правильнее привязывать адрес к каждой поставке и дополнительно хранить у клиента список адресов и «адрес по умолчанию» для подписки.
Сначала фиксируйте простые правила: группировка по районам, учет окон времени и вместимости машины, плюс базовое время на остановку. Этого достаточно, чтобы маршруты стали повторяемыми, а позже можно усложнять логику, не ломая календарь и статусы.
Нужен журнал событий: кто изменил, когда, что было «до» и «после», и почему. Это резко снижает конфликты «кто обещал» и помогает быстро разбирать спорные случаи по звонкам и недоставкам.
Проверяйте сквозной сценарий на 10–20 реальных поставках: пауза на неделю, перенос одной доставки, разовая смена адреса, отметка результата курьером. Если реестр клиентов, календарь и маршрут показывают одно и то же без дублей и пропаж, систему можно отдавать в пилот.