Сайт, карточка и телефония для производства электрощитов: от пустой выдачи до первого звонка
Производитель электрощитов и низковольтных комплектных устройств из Калининграда работал по рекомендациям: ни сайта, ни карточек на картах, офисный номер из сертификатов оставался без ответа. С середины августа по начало сентября 2026 собран полный комплект: сайт на Astro, карточка в Яндекс Бизнесе, виртуальная АТС с голосовым меню, чат-консультант на GigaChat, разметка, заголовки безопасности, резервные копии с проверкой и ежедневная сводка.
Заказчик слышал о компании от проектировщика, в интернете её не было
Производство в Калининграде: ГРЩ, ВРУ, АВР, щиты учёта и освещения, шкафы автоматики по однолинейной схеме заказчика. Два действующих сертификата соответствия ЕАЭС, собственные технические условия, паспорт на каждое изделие. Заказы приходили по рекомендациям и от проектировщиков.
Снабженец, услышавший название, набирал его в поиске и не находил ничего: сайта не было, карточек на картах и в справочниках тоже. В агрегаторах реестров лежали номера пятилетней давности. Верх выдачи по запросам о производстве щитов в городе занимала компания из другого региона.
Офисный номер стоял в сертификатах и паспортах изделий, за него платили каждый месяц, и в офисе за ним никто не сидел. Первая настройка виртуальной АТС дала входящий, который сбрасывался за 0 секунд без гудка: звонивший слышал тишину и обрыв. Причина нашлась в карточке пользователя, о ней ниже.
Один комплект: сайт, карточка, телефон
Все части опираются на один файл подтверждённых фактов: число попадает на сайт, в карточку и в корпус чат-консультанта только из документа или из слов владельца. Правило записано в план до первой строки текста: у заказчика-юрлица проверка поставщика по реестрам занимает минуту, и одно расхождение обнуляет доверие ко всей странице.
Единый файл подтверждённых фактов; 38 минут голосового разбора владельца расшифрованы локально, без внешних сервисов
Astro 5, восемь страниц, две сборки: свой домен и демонстрационный подкаталог; форма с загрузкой однолинейной схемы
Служба на сервере: заявка сначала на диск, потом в Telegram; согласие и тип вложения проверяются на сервере
Виртуальная АТС Ростелекома: голосовое меню на три отдела, дозвон на мобильные, перенос офисного номера
Карточка в Яндекс Бизнесе, разметка LocalBusiness, IndexNow, заголовки безопасности, резервные копии с проверкой, вечерняя сводка
Числа только из документов
Владелец прошёл по черновику голосом: запись в 38 минут расшифрована локально, на своей машине, потому что это внутренний разговор о бизнесе. Сверка сайта с разбором по 36 пунктам дала 33 совпадения; одно расхождение было по существу: страница продукции обещала подбор комплектации без однолинейной схемы, по словам владельца без схемы щит не собирают. Абзац переписан. Заглушек «уточняется» в первой версии было 32; к концу правок не осталось ни одной.
Верхняя цифра на главной, 6300 А, взята из сертификата и собственных технических условий; на странице продукции рядом стоит основной поток производства до 630 А с объяснением, где проходит граница конструкции. Раздел о поставке в остальную Россию написан после разбора первоисточников: область входит в особую экономическую зону, груз при вывозе проходит таможенный контроль, для покупателя это обычная поставка внутри страны. Названная в разговоре цифра отгрузок снята с сайта до подтверждения. Отдельным проходом 31 противопоставление переписано в утвердительную форму, повторов между страницами стало 16 → 4.
Две сборки и три запрета на индексацию
Сайт на Astro 5 и Tailwind 4, статика, восемь страниц, графика своя: 16 значков на общей сетке и однолинейная схема типового щита с правдоподобными, но ничьими данными, потому что на скане настоящей схемы читается объект заказчика. Пока домена не было, сайт собирался подкаталогом уже работающего домена с сертификатом: заказчик смотрел демонстрацию по https без записи DNS. Проверка ссылок ловит и ссылку в никуда, и ссылку без префикса: ссылка логотипа вела на «/», то есть на главную домена-носителя, и обычная проверка «цель существует» этого не видела.
До согласования содержания сайт был закрыт от поисковиков тремя способами сразу: noindex в разметке, заголовок X-Robots-Tag и robots.txt. Снимать все три пришлось одновременно: заголовок сильнее мета-тега и один держал бы сайт вне индекса. Флаг снятия прописан в скрипт выкладки, иначе следующая выкладка закрыла бы сайт обратно. Время кэширования DNS уменьшено с суток до часа: при переезде на запасной сервер адрес обновится у посетителей за час.
Форма, которая не теряет схему
У щитовиков заявка почти всегда идёт с однолинейной схемой. Заявка сначала пишется на диск и только потом уходит в Telegram; вложения идут в группу менеджеров отдельными сообщениями, до 5 файлов. Пределы 20 МБ на файл и 60 МБ на заявку названы на странице теми же числами, что стоят в службе. Проверки, которые жили только в браузере, перенесены на сервер: согласие на обработку данных, тип файла, скрытое поле-ловушка и время заполнения; отправка быстрее двух секунд набрана машиной и отсекается молча.
Отказ раньше выглядел как успех: при любой ошибке человек попадал на страницу благодарности. Теперь страница показывает причину и телефоны; файл, не прошедший проверку, доходит до менеджера отдельным блоком «не приняты вложения». Приём сообщений из Telegram терял обращения: текст уходил в группу с разметкой HTML без экранирования, и знак «меньше» в бытовой фразе щитовика, «ввод < 630 А», ронял всё сообщение, при этом отправитель получал автоответ «принято». Экранирование поставлено, в журнал пишется тело ответа Telegram.
Телефония: почему входящие сбрасывались за 0 секунд
Виртуальная АТС Ростелекома была подключена, правило маршрутизации исправно: активно, круглосуточно, на группу. Входящий доходил до линии и сбрасывался мгновенно, в протоколе вызова был единственный шаг «вызов на входящую линию». Причина нашлась в карточке единственного пользователя: мобильный в сценарии вызова выключен переключателем, SIP-устройств не прикреплено ни одного, и АТС было некуда звонить. В схеме сценария выключенное плечо отличается только серым цветом рамки, поэтому проверять нужно карточку каждого номера. Заодно поправлены часовой пояс домена, из-за которого журнал звонков врал на час, номер для исходящих по умолчанию и уведомления голосовой почты, стоявшие «не отправлять».
Собрана структура: три пользователя в рамках тарифа — дирекция, бухгалтерия, технический отдел, у каждого свой мобильный; линий стало 6/6 против прежних 2/2. Голосовое меню озвучено синтезом, 13,6 с: по цифре вызов уходит в отдел, по истечении ожидания — в дирекцию. Две стандартные записи, включённые в домене по умолчанию, выключены: звонивший слышал чужой текст после нашего меню и после 40 секунд гудков. Протоколы трёх реальных звонков показали, что адресация исправна: нажавший «1» на 11-й секунде соединился с дирекцией, два звонка звонившие бросили сами на 16-й и 24-й секунде. Проблема была во времени: 13,6 с меню плюс 8 с ожидания давали 22 с до первого гудка, из них 8 — тишина. Ожидание уменьшено до 6 с, до гудка стало 19,6 с; дальше сокращать можно только текстом самого меню.
Офисный номер, напечатанный в сертификатах, в домене АТС отсутствовал: проверка звонками показала, что вызовы на него в журнал не попадают вовсе. Обращение к оператору переписано с этих фактов: три требования и перечень того, что настроено с нашей стороны; перенос выполнен 1 сентября по заявке от 28 августа. Перенесённый номер пришёл со своим правилом, все вызовы в группу мимо голосового меню; правило переключено вручную, теперь оба номера ведут в одно меню. На время переноса основным на сайте стоял номер, выданный АТС; после переноса офисный вернулся в шапку, на кнопку звонка и в разметку, служебный убран с семи страниц живого сайта.
Чат-консультант на GigaChat: собран, на сайте заказчика пока не включён
Отвечает по щитам и НКУ, на вопросы без ответа собирает заявку с контактом. Движок на FastAPI с потоковой выдачей, окно чата без библиотек. Корпус, около 3200 токенов, целиком помещается в системный промпт, поэтому векторного поиска нет намеренно: поиск по такому объёму добавил бы точку отказа и шанс не подобрать нужный кусок. Половина правил — перечень того, чего бот не знает: цены, сроки, гарантия, предельный ток, марки аппаратов, объекты, номера сертификатов. По каждому пункту он говорит, что именно уточнит менеджер, и предлагает оставить телефон. Проверено вопросами по всему списку: ничего не выдумал; на вопрос о лицензии объяснил, что сборка НКУ не лицензируется, и назвал регламенты ТР ТС 004/2011 и 020/2011.
Заявка сначала на диск, потом в мессенджер, и в неё кладётся весь разговор. Сертификат Минцифры, без которого не проходит TLS со Сбером, подключён параметром соединения именно с ним: государственный корень в системном хранилище смог бы подписать для машины любой домен. Счётчик частоты запросов читал адрес из заголовка, который подставлял сам клиент: 25 запросов с вымышленными адресами прошли без единого отказа, каждый — платный вызов модели со счёта владельца. Ограничение перенесено в nginx по адресу из сокета, 20 запросов в минуту; те же 25 запросов теперь упираются в отказ. Службы ушли с root: чат работал с полным набором из 41 привилегии ядра; секреты отданы через EnvironmentFile, файлы заявок и переписки получили права 640 в каталогах 750.
К сайту заказчика окно чата не подключено: содержание сайта ещё согласуется владельцем, и бот, который бойко отвечает по несогласованному описанию услуг, опаснее его отсутствия. До включения пять шагов: согласование содержания, бот и группа менеджеров для заявок, вставка в конфиг nginx, одна строка в макете и абзац о чате в политике обработки данных.
Карточка, разметка и индексация
Карточка в Яндекс Бизнесе заведена с теми же данными, что на сайте: часы работы по будням 9:00–18:00 названы владельцем и стоят одинаково в карточке и в разметке, потому что карточка и сайт стоят в выдаче рядом, и разные ответы на один вопрос читаются как заброшенность. Разметка была Organization, юрлицо без места на карте; добавлен тип LocalBusiness с часами, областью поставки «Россия», ссылкой на карточку и координатами. Ссылка связывает сайт и карточку в обе стороны, без неё поисковик видит две разные компании с одним названием. Число со страницы карточки в Картах оказалось центром видимой области, мимо на два километра; координаты проверены прямым геокодированием по дому и обратным по точке.
Индексация открыта по решению владельца вместе со счётчиком Яндекс Метрики с Вебвизором и подтверждением прав в Вебмастере и Search Console. К 25 августа Google держал в индексе шесть страниц, Яндекс пришёл впервые 27 августа. Выкладка сама сообщает об изменении по IndexNow: адреса берутся из карты сайта, первый вызов вернул 202 на семи адресах. 6 сентября Вебмастер показал у карты «число ссылок в файле — 1» и ноль страниц в поиске: адреса лежат во вложенном файле двухуровневой карты, и по журналу nginx робот девять раз забирал индекс, за вложенным файлом не ходил. В robots.txt добавлена вторая строка Sitemap прямо на файл с адресами, семь адресов отправлены на переобход.
- Значок сайта в четырёх файлах: робот Вебмастера искал /favicon.ico и получал 404, хотя SVG отдавался
- Обложка ссылки 1200×630 из кадра цеха для мессенджеров и своя страница 404 с разделами и телефонами; код ответа остался 404
- Описания страниц укорочены со 174 и 176 знаков до 132 и 131: поисковик показывает около 160, и концы фраз уходили в многоточие
Сервер: заголовки, права, копии
add_header в nginx не наследуется вниз, если во вложенном блоке есть хоть один свой: на CSS, шрифтах и картинках было ноль заголовков безопасности. Набор вынесен в отдельный файл и подключён в каждый блок, на статике теперь четыре заголовка, включая nosniff; версия сервера скрыта, TLS 1.0 и 1.1 отключены. Политика безопасности содержимого лежала в файле формата, который nginx не читает, и не отдавалась вовсе; теперь она задана в конфиге; служебный файл, отдававшийся наружу с кодом 200, закрыт. Потолков памяти у служб не было: на машине с 1,9 ГБ несколько одновременных загрузок могли выбрать всю память и остановить nginx, за которым оба сайта. Поставлены 384 МБ на форму и чат и 192 МБ на приёмник; nginx перезапускается через 5 секунд после падения. Конфигурация зеркалится в репозиторий целиком: копия отставала от боевой на 25 строк.
Резервные копии не покрывали проект вообще. Теперь в копию входят заявки, вложения, журнал чата и снимок базы знаний; секреты не копируются, они перевыпускаются за минуту. Проверка была по размеру; обрыв на середине даёт файл правильного вида и внушительного веса, который не распаковывается. Добавлены распаковка и проверка, что заявки внутри; учебное восстановление: 22 файла, все три файла заявок на месте. Через несколько дней проверка стала поднимать ложную тревогу на исправных копиях: grep -q закрывал канал после первого совпадения, tar получал SIGPIPE, и pipefail считал провалом весь конвейер — чем раньше находились заявки, тем вернее срабатывала тревога. Копии снимает вторая машина по ключу с принудительной командой, она же каждые пять минут проверяет доступность обоих сайтов; каждый её вход отмечается в журнале авторизации, и если входа нет дольше 26 часов, ежедневная сводка скажет об этом в Telegram. Строка появляется только когда плохо: две машины приглядывают друг за другом без внешних служб.
Вечерняя сводка, которая измеряет
Каждый вечер в Telegram уходит сводка: заявки за сутки, сколько человек заходило и сколько пришло из поиска. В отчёт была вписана строка «сайт закрыт от поисковиков», верная до 19 августа и печатавшаяся после, каждый вечер; теперь посетители считаются по журналу nginx при каждом запуске, и такая строка устареть не может. Первый счёт отсеивал роботов по имени агента и выдал 30 человек за сутки при двух живых: сканеры давно представляются обычным браузером. Работает поведение: шрифт запрашивает только тот, кто рисует страницу. Новый счёт даёт 29 человек за неделю против 26 у Яндекс Метрики; расхождение в три человека и есть точность метода, до правки оно было 178. В тексте сводки стоит «примерно» и указание, что точное число в Метрике.
Вёрстка на телефоне и вес страниц
На 375 px первый экран трёх страниц уезжал за правый край: элемент сетки по умолчанию не уже своего содержимого, и трек с однолинейной схемой раздувался до 586 px; после правки колонка 335 px, схема прокручивается внутри своего контейнера. Снимки производства получили WebP и запасной JPEG по 1600 и 800 px: семь кадров страницы производства 3200 КБ → 1168 КБ на компьютере и 415 КБ на телефоне, разрешение не уменьшено; главный кадр продукции 627 → 147 КБ на телефоне. Десять прогонов Lighthouse после снятия приоритета с кадра за первым экраном: LCP 2,40 → 2,10 с, вес 367 → 324 КБ, сдвиг раскладки нулевой. Типографика вшита в сборку, 830 неразрывных пробелов расставляет скрипт; контрасты по формуле WCAG: текст 17,8:1, акцент 8,0:1. Основной телефон выводился по 5–8 раз на страницу; на главной стало 8 → 6 вхождений, полный список номеров рендерится один раз.
Статика, одна машина и операторские сервисы
Статика, две сборки под свой домен и под демонстрационный подкаталог, проверка ссылок и типографика внутри сборки
Заголовки безопасности на всей статике, политика содержимого, ограничение частоты запросов, службы без root, перезапуск после падения
Приём заявок с вложениями и движок чата: сначала на диск, потом в Telegram; проверки согласия и типа файла на сервере
Чат-консультант с корпусом около 3200 токенов в системном промпте и перечнем того, чего он не знает
Голосовое меню на три отдела, дозвон на мобильные, перенос офисного номера в домен АТС
Карточка с теми же часами и телефоном, счётчик с Вебвизором, разметка LocalBusiness, уведомление поисковиков при выкладке
Замеры до и после
до первого гудка: 13,6 с голосового меню и 6 с ожидания; нажавший цифру соединяется раньше
семь кадров страницы производства; на компьютере 1168 КБ, разрешение 1600 px сохранено
десять прогонов Lighthouse; вес страницы 367 → 324 КБ, сдвиг раскладки нулевой
Отбор роботов по имени агента пропускал сканеры, представляющиеся обычным браузером: 30 человек за сутки при двух живых. Отбор по поведению, запросу шрифта, дал 29 человек за неделю против 26 у Метрики. В сводке стоит «примерно»: число из журнала даёт порядок величины, точное число в Метрике.
Сайт работает на своём домене, восемь страниц, форма принимает заявки со схемами, карточка в Яндекс Бизнесе заведена, офисный номер из сертификатов отвечает голосовым меню и дозванивается до мобильных сотрудников. К 25 августа Google держал в индексе шесть страниц, Яндекс пришёл 27 августа; после правки карты сайта 6 сентября семь адресов отправлены на переобход. Заказчик, набравший название компании, теперь находит сайт, карточку и работающий телефон.
Чат-консультант собран и проверен на вопросах, ответов на которые у него нет: ничего не выдумал. На сайте заказчика он пока не включён, и это осознанно: сначала владелец согласует содержание, по которому бот будет отвечать.
Честное ограничение: весь боевой сайт стоит одной машиной на одной площадке. 18 августа авария оператора связи на площадке уронила его на несколько часов вместе с соседним сервером, к которому правки не относились. Поэтому время кэширования DNS уменьшено до часа, копии уходят на вторую машину и проверяются распаковкой: переезд на запасной сервер займёт час на стороне посетителей.
С 18 августа по 6 сентября в журнале работ 92 записи, и каждая заканчивается проверкой на живом сайте: коды ответа страниц, заголовки, вёрстка на 375 px, сквозная заявка с вложением, реальные звонки по протоколам АТС.
Где ещё ложится тот же комплект
За кейсом стоит типовая задача «первое присутствие действующего бизнеса в интернете»: сайт, карточка и телефон собираются за один заход и держатся на одном файле фактов.
- → Производство или мастерская без сайта — заказчик проверяет поставщика по реестрам за минуту; сайт, карточка и реквизиты закрывают проверку
- → Городской номер, за которым никто не сидит — виртуальная АТС с меню по отделам и дозвоном на мобильные, с проверкой по протоколам реальных звонков
- → Сайт есть, заявки теряются — приём на диск до отправки в мессенджер, вложения отдельными сообщениями, причина отказа видна и человеку, и менеджеру
- → Карточка и сайт расходятся — часы, телефон и адрес из одного источника, разметка LocalBusiness со ссылкой на карточку
- → Чат-консультант для узкой ниши — корпус фактов помещается в системный промпт, половина правил перечисляет то, чего бот не знает
- Единый файл фактов: число попадает на сайт, в карточку и в корпус чата только из документа или слов владельца
- Приём заявок «сначала на диск, потом в мессенджер» с вложениями отдельными сообщениями и проверками на сервере
- Проверка копий распаковкой и по наличию заявок; две машины приглядывают друг за другом по журналу авторизации
- Порядок проверки виртуальной АТС: карточка каждого номера, часовой пояс, стандартные записи, замер времени до первого гудка по протоколам
- Вечерняя сводка, которая измеряет состояние на каждом запуске и печатает строку о копиях только когда плохо
Если у производства нет сайта и на офисный номер никто не отвечает — это собирается одним комплектом
Начинаем с файла фактов: что подтверждено документами и словами владельца. Дальше сайт, карточка и телефония собираются на нём, и каждая правка проверяется на живом сайте и реальными звонками.
Похожие кейсы
Платформа автоматизации маркетинга: десктоп → Telegram → веб
Выросла из программы на Tkinter в Telegram-бота и веб-приложение на Next.js + FastAPI + PostgreSQL + Celery с…
Swift/SwiftUI: первая версия за 9 недель — от старта до App Store
Приложение для iOS 17+: расписание и напоминания (24 ч / 1 ч / 10 мин), Speech Framework проверяет…
PWA для фитнес-студии: 1,2 МБ против 47 МБ у обычного приложения
Ставится на телефон как обычное приложение (PWA): работает без сети через Service Worker, уведомления на iOS…
Аудит за 9 900 ₽ — с конкретным отчётом и сметой
Расскажу что внедрить в вашем бизнесе в первую очередь, какая будет окупаемость, и нужен ли вообще AI для вашей задачи (иногда — нет).
Или просто напишите свой вопрос — отвечу в течение 2 часов