kosareva.cloud

Обезличивание персональных данных перед отправкой в нейросеть

Шлюз стоит между вашим кодом и моделью. Он находит в запросе чувствительные данные и подменяет их заглушками. Модель работает с обезличенным текстом. В ответе заглушки разворачиваются обратно, и вы получаете настоящие данные.

один запрос, три состояния
Отправил ваш код
Составь ответ клиенту: Петров И. С.,
почта petrov@acme.ru, ИНН 7707083893
Ушло в модель
Составь ответ клиенту: Петров И. С.,
почта [[EMAIL_1]], ИНН [[INN_1]]
Вернулось вам
Здравствуйте! Мы написали на petrov@acme.ru

Фамилия здесь намеренно осталась на месте: ФИО пока не распознаются — почему.

Зачем это нужно

Запрос в зарубежную модель — это передача текста за пределы вашего контура. Всё, что попало в промпт, попало и туда.

Трансграничная передача

Если в промпте нет персональных данных, вопрос об их передаче за границу не возникает вовсе. Это проще, чем обосновывать такую передачу.

Логи на стороне провайдера

Запрос хранится у провайдера модели столько, сколько написано в его политике, и читается его сотрудниками при разборе инцидентов. Заглушку читать бесполезно.

Человек в цикле

Данные утекают не только из кода: их вставляют в промпт руками, копируют из письма, шлют в поддержку. Шлюз чистит запрос независимо от того, кто его составил.

Как это работает

Соответствие «заглушка → оригинал» живёт только в памяти одного запроса. На диск оно не пишется и в журнал не попадает.

У вас. Запрос уходит как обычно

Тот же код, тот же SDK, тот же ключ. Изменился только адрес, на который идёт запрос.

Шлюз. Данные заменяются заглушками

Одно и то же значение получает одну и ту же заглушку во всём запросе — модель понимает, что это один и тот же человек, и отвечает связно.

Модель. Видит обезличенный текст

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

Что распознаётся

Всё, что можно проверить контрольной суммой или строгим форматом, проверяется. Поэтому «заказ 1234567890» не будет принят за ИНН, а «версия 1.2.3» — за IP-адрес. Ложное срабатывание ломает работающую задачу молча, и мы предпочитаем его не допускать.

EMAIL
Адрес электронной почты
petrov@acme.ru
PHONE
Телефон
+7 995 154-15-35
INN
ИНН, 10 и 12 знаков
с проверкой контрольной суммы
SNILS
СНИЛС
с проверкой контрольного числа
CARD
Номер банковской карты
проверка по алгоритму Луна
ACCOUNT
Расчётный счёт
40702810100000000123
OGRN
ОГРН и ОГРНИП
13 и 15 знаков, с контрольной суммой
PASSPORT
Паспорт РФ
только рядом со словом «паспорт»
IP
Публичный IP-адрес
служебные 127.0.0.1 и 192.168.х.х не трогаем
SECRET · PRIVATE_KEY
Ключи и токены в коде
OpenAI, Anthropic, AWS, GitHub, Slack, Google, Yandex, JWT, приватные ключи
DB_URL · PASSWORD
Строки подключения и пароли
postgres://app:•••@host/db
IBAN · BIC · CVV
Банковские реквизиты
IBAN с проверкой mod 97, БИК, код CVV рядом с подписью
DRIVER_LICENSE
Водительское удостоверение
только рядом со словами «в/у», «права»
CAR_PLATE · VIN · OSAGO
Автомобиль
А123ВС 77 · XTA2109… · ХХХ 0123456789
MAC
MAC-адрес устройства
00:1A:2B:3C:4D:5E
DATE · URL · ENTROPY
По явному включению
даты, ссылки и токены без префикса — только заголовком X-Guard-Types
X-Guard-Deny
Запретить, а не маскировать
Номера карт или ключи нельзя отправлять даже обезличенными — такой запрос не уйдёт в модель вовсе, вернётся ошибка со счётчиками.
X-Guard-Files
Вложения под контролем
Картинку или файл нельзя обезличить частично. Запрет по видам: изображения, аудио, любые файлы.
Подсказка модели
Модель понимает заглушки
Когда что-то замаскировано, модель получает короткую инструкцию: считать заглушки настоящими значениями и переносить их в ответ как есть.

Чего пока нет — и почему

ФИО, адреса и названия компаний регулярными выражениями не берутся. Правило, достаточно широкое, чтобы поймать «Петров», поймает заодно половину обычных слов — и молча испортит запрос. Эти типы во второй очереди: их будет распознавать отдельная модель, работающая на нашей стороне.

Мы говорим об этом прямо, потому что маскирование, которому нельзя доверять, опаснее его отсутствия: на него полагаются и перестают проверять.

Подключение

Меняется адрес — всё остальное остаётся как было.

Python · openai
from openai import OpenAI

client = OpenAI(
    api_key="ВАШ_КЛЮЧ",
    base_url="https://api.kosareva.cloud/guard/v1",
)

resp = client.chat.completions.create(
    model="gpt-4o",
    messages=[{
        "role": "user",
        "content": "Клиент petrov@acme.ru, ИНН 7707083893",
    }],
)
cURL
curl https://api.kosareva.cloud/guard/v1/chat/completions
  -H "Authorization: Bearer ВАШ_КЛЮЧ"
  -H "Content-Type: application/json"
  -d '{
    "model": "gpt-4o",
    "messages": [
      {"role": "user", "content": "Клиент petrov@acme.ru"}
    ]
  }'

Управление заголовками

X-Guard-Types: EMAIL,PHONE
Маскировать только перечисленные типы. Без заголовка — все.
X-Guard-Off: true
Пропустить запрос без изменений. Удобно, чтобы сравнить поведение модели.
X-Guard-Masked
Приходит в ответе: сколько чего было замаскировано, например EMAIL=1,INN=1. Только счётчики, без значений.

Предпросмотр без отправки

Отдельный адрес показывает, что будет замаскировано, и никуда не обращается. Прогоните на нём свои настоящие промпты до того, как переключите боевой трафик.

POST /guard/v1/guard/preview

{"found": [{"type": "EMAIL", "value": "petrov@acme.ru"}],
 "preview": ["Клиент [[EMAIL_1]]"]}

Что происходит с данными

Соответствия не сохраняются

Таблица «заглушка — оригинал» существует, пока обрабатывается запрос, и исчезает вместе с ним. Базы масок нет.

В журнал идут только счётчики

Ни текст запроса, ни найденные значения не логируются. Шлюз не должен сам стать тем местом утечки, от которого защищает.

Маскируются и вызовы инструментов

Аргументы function calling чистятся так же, как текст сообщений: через них данные утекают ровно тем же способом.

Ключи и деньги там же, где были

Шлюз передаёт ваш ключ дальше нетронутым и ничего о вас не знает. Лимиты, баланс и статистика считаются как раньше.

Отдельный адрес, а не общий рубильник

У тех, кто маскирование не подключал, путь запроса не изменился. Новый код стоит только на пути тех, кто его выбрал.

Написано нами

Это наш код, а не перепродажа чужого сервиса. Данные не уходят ещё и третьей стороне «на проверку».

Частые вопросы

Модель не запутается, увидев заглушки вместо данных?

Одинаковые значения получают одинаковые заглушки, поэтому связи в тексте сохраняются: модель видит, что в первом абзаце и в третьем — один и тот же адрес. Смысловая часть промпта не меняется вовсе.

Что будет, если модель придумает свою заглушку?

Разворачиваются только те заглушки, которые шлюз сам поставил в этом запросе. Незнакомая останется в ответе просто текстом — подставить вместо неё чужие данные невозможно.

Работает ли это с потоковым ответом?

Да. Заглушка почти всегда разрывается между кусками ответа, поэтому шлюз придерживает хвост от незакрытой скобки до следующего куска. Задержка — один кусок, на глаз незаметна.

А если нужно, чтобы модель видела настоящие данные?

Заголовок X-Guard-Off: true пропускает конкретный запрос без изменений, а X-Guard-Types оставляет маскирование только для нужных типов.

Это заменяет DLP-систему?

Нет. Классическая DLP закрывает почту, файлы и съёмные носители. API Guard закрывает один конкретный канал — запросы к языковым моделям, который обычная DLP не видит: для неё это просто HTTPS к внешнему API.

Попробуйте на своих запросах

Маскирование работает с любым ключом kosareva.cloud. Начните с предпросмотра: он покажет, что нашлось бы в ваших промптах, ничего никуда не отправляя.