# Анонимизация ПДн · PII Guard API — neuraldeep.ru API

> Раздел машиночитаемой справки. Все разделы: https://neuraldeep.ru/llms.txt · всё одним файлом: https://neuraldeep.ru/llms-full.txt

Base URL: `https://api.neuraldeep.ru/v1`
Auth: `Authorization: Bearer $YOUR_KEY`

Тем же ключом можно обезличивать персональные данные (ПДн) под `/v1/pii/*`. Сервис находит ПДн в русском тексте, заменяет их тегами вида `<PII type="PERSON" gender="male" id="1" />`, а на обратном пути подставляет оригиналы обратно и **ставит имена и места в нужный падеж**. Считается на нашей GPU в России.

Два способа подключить:
- **свой пайплайн**: зовёшь `/anonymize` и `/deanonymize` сам, как в примерах ниже;
- **щит на ключе**: включается в кабинете, в разделе «Ключи», переключателем PII-Guard. После этого каждый чат-запрос с этим ключом обезличивается до модели, а ответ восстанавливается до клиента. Cursor, opencode, Open WebUI, n8n и любой OpenAI-совместимый клиент работают без правок кода. Покрыты только чат-запросы: эмбеддинги, реранк, аудио и картинки щит не трогает.

**Что находит.** 25 типов: `PERSON`, `LOCATION`, `EMAIL_ADDRESS`, `PHONE_NUMBER`, `URL`, `IP_ADDRESS`, `IP_PORT`, `DATE_TIME`, `PASSPORT`, `CREDIT_CARD`, `CVC`, `DRIVER_LICENSE`, `INN`, `KPP`, `OGRN`, `OGRNIP`, `SNILS`, `MILITARY_ID`, `BIRTH_CERTIFICATE`, `OMS`, `BANK_ACCOUNT`, `BIK`, `POSTAL_CODE`, `TELEGRAM`, `TOKEN` (ключи и токены доступа). Их же можно перечислить в `entities`; старые имена вроде `FIRST_NAME`, `CITY`, `PHONE`, `EMAIL` тоже принимаются. Незнакомый тип вернёт `422` со списком известных. Документы с контрольной суммой (ИНН, СНИЛС, карты, счета, БИК) ловят правила с проверкой суммы, имена, места, телефоны и ссылки находит нейросеть на базе ruBERT, дообученная на русских ПДн. Распознавание вероятностное: риск утечки становится сильно ниже, но гарантии, что найдено всё, нет.

**Приватность.** Тексты мы не храним. Маппинг тег → оригинал возвращается **тебе** в ответе `/anonymize` и на нашей стороне сразу удаляется. Ты держишь его у себя и присылаешь обратно в `/deanonymize`. Для учёта повторов (см. цены) мы помним на час только хеш текста, по которому сам текст не восстановить.

**Эндпоинты:**
- `POST /v1/pii/anonymize`: `{text}` или `{texts:[…]}`, опционально `entities` (список типов, если нужно ловить только часть, например `["PERSON","PHONE_NUMBER"]`). Ответ: `{anonymized, mapping, action, quota}`. `anonymized` строка для `text` и массив для `texts`, `action` равен `ANONYMIZE`, если что-то нашлось, и `NONE`, если нет.
- `POST /v1/pii/deanonymize`: `{text|texts, mapping}` → `{deanonymized, quota}`.
- `GET /v1/pii/quota`: остаток квоты подписки на день и месяц. Когда квота кончилась, приходит `429` с `Retry-After`.

**Батч.** В `texts` можно передать до 512 текстов за вызов, каждый до 1 млн знаков. Порядок ответа совпадает с порядком запроса.

**Агентные сессии.** Агент на каждом шаге присылает историю целиком. Шли каждое сообщение отдельной строкой в `texts`: сообщения, которые этот же аккаунт уже присылал за последний час, считаются входом из кеша и стоят в 10 раз дешевле, а за их выход ты не платишь. Щит на ключе делает так сам.

**Скорость.** Короткий текст обрабатывается за десятки миллисекунд, документ на 1 млн знаков около 4 секунд в первый раз и около 0,5 секунды повторно.

> 🎁 **До 20.10 включительно анонимизация бесплатна для всех**: ни ручной API, ни щит на ключе ничего не списывают, баланс не нужен, квоты подписок на это время подняты до уровня Pro. Цены ниже действуют с 21.10.

**Цены.** Считаем по токенам, как у моделей: платишь за вход и за выход, даже если ПДн в тексте не нашлось, потому что GPU всё равно поработала. Токены оцениваем по длине: примерно 2,3 знака русского текста на токен.

| что | ₽ за 1M токенов |
|---|---|
| обезличивание, вход | 5 |
| обезличивание, выход | 5 |
| вход из кеша (текст, который ты уже присылал за час) | 0,5 |
| восстановление, вход и выход | 1 и 1 |

Пример. Агент с историей 300 тыс. знаков (около 130 тыс. токенов). Первый шаг стоит около 1,3 ₽ на обезличивание. Следующий шаг с той же историей и новым сообщением на 2 тыс. знаков стоит около 7 копеек: история идёт из кеша, платишь в основном за новое сообщение.

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

```bash
# 1. обезличить, mapping из ответа сохранить у себя
curl https://api.neuraldeep.ru/v1/pii/anonymize \
  -H "Authorization: Bearer $YOUR_KEY" -H "Content-Type: application/json" \
  -d '{"text":"Иван Петров, +79161234567, живёт в Москве"}'
# → {"anonymized":"<PII type=\"PERSON\" gender=\"male\" id=\"1\" />, <PII type=\"PHONE_NUMBER\" id=\"2\" />, ...",
#    "mapping":{"<PII type=\"PERSON\" gender=\"male\" id=\"1\" />":"Иван Петров", ...}, "action":"ANONYMIZE", "quota":{...}}

# 2. восстановить ответ модели: теги → оригиналы, со склонением
curl https://api.neuraldeep.ru/v1/pii/deanonymize \
  -H "Authorization: Bearer $YOUR_KEY" -H "Content-Type: application/json" \
  -d '{"text":"Письмо для <PII type=\"PERSON\" gender=\"male\" id=\"1\" />","mapping":{...}}'
```

```python
import httpx
H = {"Authorization": "Bearer $YOUR_KEY"}
API = "https://api.neuraldeep.ru/v1"

# 1. обезличиваем текст пользователя
a = httpx.post(f"{API}/pii/anonymize", headers=H,
               json={"text": "Иван Петров, тел +79161234567, Москва"}).json()
safe, mapping = a["anonymized"], a["mapping"]

# 2. отправляем в ЛЮБУЮ модель без ПДн, просим сохранить теги
resp = httpx.post(f"{API}/chat/completions", headers=H, json={
    "model": "qwen3.6-35b-a3b",
    "messages": [{"role": "system", "content": "Теги <PII .../> оставляй в ответе как есть, не меняй и не раскрывай."},
                 {"role": "user", "content": safe}],
}).json()["choices"][0]["message"]["content"]

# 3. восстанавливаем ПДн в ответе модели тем же mapping
final = httpx.post(f"{API}/pii/deanonymize", headers=H,
                   json={"text": resp, "mapping": mapping}).json()["deanonymized"]
print(final)
```

```python
history = ["Привет, я Иван Петров", "Здравствуйте! Чем помочь?", "Мой ИНН 7707083893"]
a = httpx.post(f"{API}/pii/anonymize", headers=H, json={"texts": history}).json()
safe_history = a["anonymized"]   # массив в том же порядке
# на следующем шаге шлёшь ту же историю + новое сообщение:
# первые три строки пойдут как вход из кеша
```
