v4.0.0: дизайн Nubes, логотип, ZIP без mapping.csv внутри, CSV отдельно с датой-временем
Deploy drhider / validate (push) Waiting to run
Deploy drhider / validate (push) Waiting to run
This commit is contained in:
@@ -0,0 +1,47 @@
|
||||
# Запрос к Соннету — нумерация вместо генерации фейков (2026-07-12)
|
||||
|
||||
## Контекст
|
||||
|
||||
DrHider обфусцирует документы: ищет ПДн → заменяет на фиктивные значения.
|
||||
Сейчас используется генерация "похожих" фейков (Иванов И.И., ООО «Ромашка», +7(495)...).
|
||||
|
||||
## Проблема
|
||||
|
||||
1. **Адреса → абракадабра.** Ул. Стекольная → иг. 8ц Лжчюсвхшбр. Потому что fallback-генератор меняет кириллицу на случайную кириллицу.
|
||||
2. **Сложность.** 11 генераторов под каждый тип данных. Каждый надо поддерживать.
|
||||
3. **Ложное ощущение реальности.** Фейковые ИНН с правильной контрольной суммой выглядят как настоящие.
|
||||
|
||||
## Идея
|
||||
|
||||
Заменить всю генерацию на **нумерацию по типам:**
|
||||
|
||||
| Оригинал | Замена |
|
||||
|---|---|
|
||||
| Иванов И.И. | `Лицо_0042` |
|
||||
| ООО «НУБЕС» | `Компания_0003` |
|
||||
| ул. Стекольная, д.7 | `Адрес_0015` |
|
||||
| +7 (495) 789-41-35 | `Телефон_0007` |
|
||||
| info@nubes.ru | `Email_0004` |
|
||||
| ИНН 9706005293 | `ИНН_0002` |
|
||||
| Р/с 40702... | `Счёт_0001` |
|
||||
| договор-XXX001.docx | `Файл_0006` |
|
||||
|
||||
## Вопросы
|
||||
|
||||
1. **Плюсы/минусы** нумерации vs генерации фейков для задачи обфускации документов?
|
||||
2. **Как нумеровать?** Глобальный счётчик на каждый тип? Или в рамках одного документа?
|
||||
3. **Стоит ли сохранять формат?** Например `Телефон_0007` vs `+7 (000) 000-00-07`?
|
||||
4. **mapping.csv** — при нумерации он становится главным документом аудита. Это ок?
|
||||
5. **UUID вместо номеров?** `Лицо_a3f4b2` — лучше или хуже последовательных номеров?
|
||||
|
||||
## Текущий mapping.csv (для контекста)
|
||||
|
||||
```csv
|
||||
тип_данных,оригинал,замена
|
||||
phone,+7 (495) 789-41-35,+7 (495) 906-87-80
|
||||
email,info@nubes.ru,ypiorej@company.local
|
||||
company,"ЗАО ""XXX001""",ООО «Альянс»
|
||||
inn_ul,ИНН 9706005293,ИНН 1846691249
|
||||
text,Исполнителем Заказчику Сторонами,Кузнецов О.В.
|
||||
text,"115404, г. Москва, ул. 1-я Стекольная, д.7с2","084810, б. Ввжзгд, гф. 6-в Фтпжыобнзщ, я.8с1"
|
||||
```
|
||||
@@ -0,0 +1,54 @@
|
||||
# Запрос к Соннету — нумерация vs фейки для downstream LLM (2026-07-12)
|
||||
|
||||
## Контекст
|
||||
|
||||
Я делаю сервис **DrHider** — обфускация документов. Находит ПДн → заменяет.
|
||||
После обфускации документы идут на дальнейшую LLM-обработку — **сверка спецификаций**
|
||||
(другой сервис contracts, извлекает типы/номера/даты/контрагентов через LLM).
|
||||
|
||||
Сейчас генерация фейков: `Иванов И.И.` → `Петров А.С.`, `ООО «Ромашка»` → `ООО «Спектр»`.
|
||||
|
||||
**Проблема:** для неизвестных типов (адреса, нестандартные ID) — character-class замена
|
||||
даёт абракадабру: `ул. Стекольная` → `иг. 8ц Лжчюсвхшбр`. Downstream LLM не может это обработать.
|
||||
|
||||
## Варианты замены
|
||||
|
||||
### А. Чистая нумерация
|
||||
`Иванов И.И.` → `Лицо_0042`, `ООО «Ромашка»` → `Компания_0003`, `ул. Ленина` → `Адрес_0015`
|
||||
|
||||
Плюс: никакой абракадабры. Минус: LLM теряет контекст («Лицо_0042 заключил договор» — не понимает семантику).
|
||||
|
||||
### Б. Фейки (сейчас)
|
||||
`Иванов И.И.` → `Петров А.С.`, `ООО «Ромашка»` → `ООО «Спектр»`
|
||||
|
||||
Плюс: LLM понимает роли. Минус: сложно (11 генераторов), ложное ощущение реальности,
|
||||
для неизвестных типов — абракадабра.
|
||||
|
||||
### В. Гибрид: шаблон + номер
|
||||
`Иванов И.И.` → `Иванов_5677`, `ООО «Ромашка»` → `ООО_Технология_0034`,
|
||||
`ул. Стекольная, д.7` → `ул_Ленина_0015`, `+7 (495) 789-41-35` → `+7_495_000_0042`,
|
||||
`info@nubes.ru` → `email_0007@fake`
|
||||
|
||||
Плюс: LLM видит что это человек/компания/адрес, номер гарантирует уникальность и обфускацию.
|
||||
Минус: всё равно нужны шаблоны для каждого типа.
|
||||
|
||||
## Вопросы
|
||||
|
||||
1. Какой вариант лучше для downstream LLM-обработки (извлечение контрагентов, дат, номеров)?
|
||||
2. Вариант В — достаточно ли LLM поймёт что `Иванов_5677` это персональные данные?
|
||||
3. Для неизвестных типов — `[Данные_NNNN]` как fallback, ок?
|
||||
4. Глобальная нумерация (сквозная через все документы пакета) vs локальная (в рамках одного файла)?
|
||||
5. Стоит ли сохранять частичную структуру (например телефон `+7_495_000_0042` сохраняет формат номера)?
|
||||
|
||||
## Downstream задача (для контекста)
|
||||
|
||||
LLM в сервисе contracts получает текст документа и должна извлечь:
|
||||
- Контрагент («с кем договор»)
|
||||
- Номер и дату договора
|
||||
- Список услуг с ценами (таблица)
|
||||
|
||||
Промпт для contracts LLM (фрагмент):
|
||||
```
|
||||
Извлеки из текста: тип документа, номер, дату, контрагента.
|
||||
Верни JSON: {"type":"договор","number":"...","date":"...","counterparty":"..."}
|
||||
```
|
||||
@@ -0,0 +1,46 @@
|
||||
# Ответ Соннета v3 — нумерация вместо генерации фейков (2026-07-12)
|
||||
|
||||
## Q1. Нумерация vs фейки
|
||||
- ✅ Адреса без абракадабры, код проще, аудит прозрачнее
|
||||
- ❌ Документ нечитаем (`Лицо_0042 заключил договор с Компания_0003`)
|
||||
- Вывод: для аудита/хранения — отлично, для показа людям — фейки лучше
|
||||
|
||||
## Q2. Глобальный счётчик на весь пакет
|
||||
Одна сущность в разных документах → один номер. `TwoPassObfuscator` хранит counters.
|
||||
|
||||
## Q3. Сохранять формат?
|
||||
Рекомендация: `Тип_NNNN` — проще всего, аудит максимально прозрачен.
|
||||
|
||||
## Q4. mapping.csv — главный документ аудита
|
||||
Да, это улучшение. mapping.csv — секретный ключ деобфускации.
|
||||
|
||||
## Q5. Номера vs UUID
|
||||
Номера (`Лицо_0042`) — лучше для читаемости и аудита.
|
||||
|
||||
---
|
||||
|
||||
## План изменений
|
||||
|
||||
### Удалить
|
||||
- `drhider/generators/` — все 12 файлов
|
||||
- `drhider/checksum.py` — больше не нужен (ИНН без контрольных сумм)
|
||||
- `drhider/random_utils.py` — больше не нужен
|
||||
|
||||
### Изменить
|
||||
- `scanner.py`: добавить `TYPE_PREFIXES` + `_next_token()`, убрать импорты генераторов
|
||||
- `obfuscator.py`: `TwoPassObfuscator` хранит `counters` dict
|
||||
- `config.py`: убрать словари имён/городов (RU_SURNAMES, ...)
|
||||
|
||||
### Новая логика замены
|
||||
```python
|
||||
TYPE_PREFIXES = {
|
||||
"person_name": "Лицо", "company": "Компания", "phone": "Телефон",
|
||||
"email": "Email", "address": "Адрес", "inn": "ИНН", ...
|
||||
}
|
||||
_FALLBACK = "Данные"
|
||||
|
||||
def _next_token(entity_type, counters):
|
||||
prefix = TYPE_PREFIXES.get(entity_type, _FALLBACK)
|
||||
counters[prefix] = counters.get(prefix, 0) + 1
|
||||
return f"{prefix}_{counters[prefix]:04d}"
|
||||
```
|
||||
@@ -0,0 +1,19 @@
|
||||
# Ответ Соннета v4 — гибридный формат замен (2026-07-12)
|
||||
|
||||
## Итог: Вариант В (шаблон + номер)
|
||||
|
||||
| Тип | Формат замены | Пример |
|
||||
|---|---|---|
|
||||
| ФИО | `Фамилия_NNNN` | `Иванов_5677` |
|
||||
| Компания | `ООО_Слово_NNNN` | `ООО_Технология_0034` |
|
||||
| Адрес | `ул_Шаблон_NNNN` | `ул_Ленина_0015` |
|
||||
| Телефон | `+7_код_000_NNNN` | `+7_495_000_0042` |
|
||||
| Email | `email_NNNN@fake` | `email_0007@fake` |
|
||||
| ИНН | `ИНН_NNNNNNNNNN` | `ИНН_0000000042` |
|
||||
| Неизвестный тип | `[Тип_NNNN]` | `[Адрес_0023]` |
|
||||
|
||||
## Ключевые принципы
|
||||
1. **Читаемо человеком** — не ужиматься, пусть будет естественно
|
||||
2. **Однозначно для LLM** — префикс указывает тип сущности
|
||||
3. **Глобальная нумерация** — одна сущность = один номер во всех файлах пакета
|
||||
4. **Цены/суммы** — не обфусцировать (нужны для downstream сверки)
|
||||
+51
-59
@@ -1,71 +1,63 @@
|
||||
тип_данных,оригинал,замена
|
||||
text,"""****XXX****001****""","""****IPD****084****"""
|
||||
text,"""НУБЕС""","""ФИОЩЦ"""
|
||||
phone,+7 (495) 789-41-35,+7 (343) 986-75-93
|
||||
email,info@nubes.ru,bxkuno@company.local
|
||||
company,"ЗАО ""****XXX****001****""",ООО «Спектр»
|
||||
company,"ЗАО ""XXX001""",ЗАО «Меридиан»
|
||||
inn_ul,ИНН 9706005293,ИНН 9325731296
|
||||
text,Исполнителем Заказчику Сторонами,Морозов М.П.
|
||||
kpp,КПП 772401001,КПП 051543039
|
||||
ks,Кор/сч 30101810400000000225,Кор/сч 30101434381368067539
|
||||
ogrn,ОГРН 1207700098759,ОГРН 1094103489237
|
||||
phone,+7 (495) 789-41-35,+7 (495) 906-87-80
|
||||
email,info@nubes.ru,ypiorej@company.local
|
||||
company,"ЗАО ""****XXX****001****""",АО «Прогресс»
|
||||
company,"ЗАО ""XXX001""",ООО «Альянс»
|
||||
inn_ul,ИНН 9706005293,ИНН 1846691249
|
||||
text,Исполнителем Заказчику Сторонами,Кузнецов О.В.
|
||||
kpp,КПП 772401001,КПП 350443068
|
||||
ks,Кор/сч 30101810400000000225,Кор/сч 30101201490272090211
|
||||
ogrn,ОГРН 1207700098759,ОГРН 1048672318430
|
||||
company,"ООО ""НУБЕС""",ООО «Спектр»
|
||||
text,"Обязанности Заказчика
|
||||
Своевременно",Кузнецов А.И.
|
||||
Своевременно",Степанов А.В.
|
||||
text,"Обязанности Исполнителя
|
||||
Оказывать",Новиков В.Е.
|
||||
Оказывать",Петров П.Е.
|
||||
text,"Ответственность Заказчика
|
||||
Заказчик",Алексеев М.О.
|
||||
Заказчик",Новиков А.М.
|
||||
text,"Ответственность Исполнителя
|
||||
Исполнитель",Новиков А.П.
|
||||
company,ПАО Сбербанк,АО «Стандарт»
|
||||
Исполнитель",Попов О.М.
|
||||
company,ПАО Сбербанк,АО «Формат»
|
||||
text,"Права Заказчика
|
||||
Заказывать",Смирнов А.П.
|
||||
Заказывать",Морозов Е.В.
|
||||
text,"Права Исполнителя
|
||||
Самостоятельно",Соколов Д.И.
|
||||
rs,Р/с 40702810738000174030,Р/с 40702435046811293176
|
||||
text,Степаненко Василия Сергеевича,Степанов Н.М.
|
||||
text,договор-XXX001-03700.docx,гясдшгя-QED215-71477.xeko
|
||||
text,№ 03700_1,№ 19790_4
|
||||
Самостоятельно",Новиков П.О.
|
||||
rs,Р/с 40702810738000174030,Р/с 40702701822898587344
|
||||
text,Степаненко Василия Сергеевича,Новиков И.В.
|
||||
text,ФИО,ВИП
|
||||
text,№ 03700_1,№ 60846_8
|
||||
|
||||
text,допник-1-XXX002-01200_3.doc,зжзньф-2-ZTD398-75400_3.hnl
|
||||
|
||||
phone,+7 (495) 789-41-35,+7 (812) 636-00-61
|
||||
text,"115404, г. Москва, Вн. Тер. Г. Муниципальный округ Бирюлево Восточное, ул. 1-я Стекольная, д.7 стр. 2","592106, ж. Нквзлч, Лв. Бъи. А. Ениефьзсшашъя жцбса Нцмяеэвз Лшлцурбзц, вж. 0-й Лахалфусщд, ц.9 юпо. 1"
|
||||
text,"115404, г. Москва, ул. 1-я Стекольная, д.7с2","755298, д. Мцръьб, юм. 9-з Хщзддгэгтъ, д.7ъ9"
|
||||
text,9706005293,3297104983
|
||||
email,info@nubes.ru,rlvti@example.ru
|
||||
company,"АО ""****XXX****003****""",ЗАО «Импульс»
|
||||
company,"АО ""XXX003""",ООО «Спектр»
|
||||
inn_ul,ИНН 9706005293,ИНН 4115676360
|
||||
kpp,КПП 772401001,КПП 761577138
|
||||
ks,Кор/сч 30101810400000000225,Кор/сч 30101181264373851255
|
||||
ogrn,ОГРН 1207700098759,ОГРН 1759258523572
|
||||
company,ПАО Сбербанк,АО «Прогресс»
|
||||
rs,Р/с 40702810738000174030,Р/с 40702665883135798793
|
||||
text,Степаненко В.С.,Смирнов С.Д.
|
||||
text,Степаненко Василия Сергеевича,Лебедев Н.С.
|
||||
phone,+7 (495) 789-41-35,+7 (343) 365-60-01
|
||||
text,"115404, г. Москва, Вн. Тер. Г. Муниципальный округ Бирюлево Восточное, ул. 1-я Стекольная, д.7 стр. 2","136627, г. Езэхгъ, Оз. Сгю. В. Лицнбьстлэзло якерд Ыэстйнвл Цлифвнэбщ, ул. 5-т Ффднкомъщо, у.8 шгэ. 7"
|
||||
text,"115404, г. Москва, ул. 1-я Стекольная, д.7с2","084810, б. Ввжзгд, гф. 6-в Фтпжыобнзщ, я.8с1"
|
||||
email,info@nubes.ru,qifdckke@org.example.ru
|
||||
company,"АО ""****XXX****003****""",АО «Синтез»
|
||||
company,"АО ""XXX003""",ООО «Импульс»
|
||||
inn_ul,ИНН 9706005293,ИНН 3686281037
|
||||
kpp,КПП 772401001,КПП 831943119
|
||||
ks,Кор/сч 30101810400000000225,Кор/сч 30101659188332581128
|
||||
ogrn,ОГРН 1207700098759,ОГРН 1475471132267
|
||||
company,"ООО ""НУБЕС""",ООО «Прогресс»
|
||||
company,ООО «НУБЕС»,ООО «Синтез»
|
||||
company,ПАО Сбербанк,АО «Импульс»
|
||||
rs,Р/с 40702810738000174030,Р/с 40702719106800760870
|
||||
text,Степаненко В.С.,Павлов В.С.
|
||||
text,Степаненко Василия Сергеевича,Михайлов В.Н.
|
||||
|
||||
text,До г. Москва ул. 1я Стекольная д7 стр. 5,Чт е. Арюомп ус. 9м Рклшппкэиъ ж1 тхн. 3
|
||||
company,"ЗАО ""XXX001""",ООО «Синтез»
|
||||
text,От г. Москва ул. Бутлерова д. 7,Эр с. Эануен ьч. Ичмсжюхгб т. 5
|
||||
text,03700_1,20847_0
|
||||
company,"ЗАО ""XXX001""",ООО «Сфера»
|
||||
company,"ООО ""НУБЕС""",ЗАО «Гарант»
|
||||
text,г. Москва,с. Щйзьзф
|
||||
text,ул. 1я Стекольная д7 стр. 5,иг. 8ц Лжчюсвхшбр б1 йук. 7
|
||||
text,ул. Бутлерова д. 7,чт. Фкъяъзгра а. 2
|
||||
|
||||
text,20.12.2025,74.68.7738
|
||||
text,20.12.2025г.,92.50.1170в.
|
||||
text,29.01.2026,09.96.9732
|
||||
text,FILE: спецификация-XXX003-01300_2.docx,KKOB: вскъцгосфпкр-ADB597-48338_5.ieyo
|
||||
company,"АО ""XXX003""",ЗАО «Технология»
|
||||
text,М.П.,Х.Л.
|
||||
company,"ООО ""НУБЕС""","ЧЩЭ ""ЩНРЬА"""
|
||||
text,Степаненко В.С.,Петров П.С.
|
||||
text,г. Москва,л. Щцсмнэ
|
||||
text,№01300_2,№72987_6
|
||||
company,"АО ""XXX003""",ЗАО «Меридиан»
|
||||
company,"ООО ""НУБЕС""",ЗАО «Импульс»
|
||||
text,Степаненко В.С.,Фёдоров П.С.
|
||||
text,№01300_2,№84484_0
|
||||
|
||||
text,01.02.2026,30.99.0061
|
||||
text,01.02.2026г.,88.29.7250а.
|
||||
company,ЗАО «ХХХ001»,ЗАО «Альянс»
|
||||
company,"ООО ""НУБЕС""","БУД ""ЕЦКЫМ"""
|
||||
text,Степаненко В.С.,Петров А.В.
|
||||
text,г. Москва,ц. Чистфб
|
||||
text,спецификация-ХХХ002-01200_3.docx,жлтидюжсабеп-ЙДЮ718-50096_1.toqa
|
||||
text,№01200_3,№77153_0
|
||||
company,ЗАО «ХХХ001»,АО «Сфера»
|
||||
company,"ООО ""НУБЕС""",АО «Сфера»
|
||||
text,Степаненко В.С.,Алексеев С.С.
|
||||
text,№01200_3,№68396_3
|
||||
|
||||
|
@@ -1,7 +1,7 @@
|
||||
**************Договор******** ****************на оказание технологических услуг******
|
||||
№ 19790_4
|
||||
№ 60846_8
|
||||
|
||||
**ООО «Спектр»** именуемое в дальнейшем "Заказчик", в лице Генерального директора ФИО, действующего на основании Устава, и **ООО **"**НУБЕС**", именуемое в дальнейшем "Исполнитель", в лице Генерального директора Степанов Н.М., действующего на основании Устава, с другой стороны, вместе именуемые "Стороны", заключили настоящий Договор о нижеследующем:
|
||||
**АО «Прогресс»** именуемое в дальнейшем "Заказчик", в лице Генерального директора ВИП, действующего на основании Устава, и **ООО **"**НУБЕС**", именуемое в дальнейшем "Исполнитель", в лице Генерального директора Новиков И.В., действующего на основании Устава, с другой стороны, вместе именуемые "Стороны", заключили настоящий Договор о нижеследующем:
|
||||
# ТЕРМИНЫ И ОПРЕДЕЛЕНИЯ
|
||||
**Услуги **– оказываемые Исполнителем Заказчику технологические услуги в области компьютерных и телекоммуникационных технологий и информационной безопасности, размещение серверов на технической площадке (colocation), организация канала связи, обеспечение бесперебойного электропитания и охлаждения, предоставление готовой технической инфраструктуры, профессиональное техническое обслуживание оборудования в режиме 24/7/365, подключение к сети Интернет по высокоскоростным каналам связи, оказываемые Исполнителем Заказчику. Услуги подразделяются на Инсталляционные, Абонентские (ежемесячные), Тарифицируемые и разовые (дополнительные). Полный перечень и описание оказываемых Услуг приводятся в Спецификациях, утверждаемых Сторонами в виде Приложения №1 к Договору, являющегося его неотъемлемой частью (далее – «Спецификация»).
|
||||
**Инсталляционные услуги** – Услуги по установке, настройке и включению в сетевую инфраструктуру Исполнителя оборудования и/или программного обеспечения, необходимого для предоставления Заказчику Абонентских и Тарифицируемых Услуг.
|
||||
@@ -25,20 +25,20 @@
|
||||
Период оказания Услуг по настоящему Договору, подлежащий оплате Заказчиком, начинается с даты подписания Сторонами Акта начала оказания Услуг или с даты начала Услуг, согласованной Сторонами в Спецификации, и заканчивается в момент истечения срока действия, прекращения или расторжения настоящего Договора, если иное не установлено настоящим Договором или письменно не согласованно Сторонами.
|
||||
Технические требования к оказанию Услуг указаны в Соглашении об уровне обслуживания и Технических условиях.
|
||||
# ПРАВА И ОБЯЗАННОСТИ СТОРОН
|
||||
## Соколов Д.И. определять количество специалистов и график их работы, объем вычислительных ресурсов и программного обеспечения, а также других ресурсов, необходимых для оказания Услуг. В случае необходимости Исполнитель имеет право привлекать для исполнения обязательств по настоящему Договору третьи стороны, при этом Исполнитель в полном объеме несет ответственность за действия привлеченных Исполнителем третьих лиц перед Заказчиком.
|
||||
## Новиков П.О. определять количество специалистов и график их работы, объем вычислительных ресурсов и программного обеспечения, а также других ресурсов, необходимых для оказания Услуг. В случае необходимости Исполнитель имеет право привлекать для исполнения обязательств по настоящему Договору третьи стороны, при этом Исполнитель в полном объеме несет ответственность за действия привлеченных Исполнителем третьих лиц перед Заказчиком.
|
||||
На основании Универсального передаточного документа (далее – «УПД»), подписываемого обеими Сторонами и счета на оплату, потребовать дополнительной оплаты затраченных ресурсов, если по вине или инициативе Заказчика в ходе исполнения настоящего Договора объем фактически оказанных Услуг превысил объем Услуг, предусмотренный условиями настоящего Договора.
|
||||
Изменять в одностороннем порядке не чаще одного раза в 6 (шесть) месяцев цены на предоставляемые им Услуги с обязательным уведомлением Заказчика в письменной форме в срок не менее чем за тридцать календарных дней до вступления в силу новых цен. Отсутствие в течение вышеуказанного срока письменного отказа от новых цен со стороны Заказчика считается его согласием с указанными изменениями. Об изменении цен по Договору Стороны подписывают дополнительное соглашение. Заказчик обязуется в течение 15 рабочих дней с даты получения уведомления Исполнителя и Дополнительного соглашения об изменении цены по Договору подписать такое Дополнительное соглашение, либо направить Исполнителю письменный мотивированный отказ от его подписания. В случае отказа Заказчика от подписания Дополнительного соглашения на условиях, предлагаемых Исполнителем, а также в случае, если в указанный срок Заказчик не направит Исполнителю письменный мотивированный отказ от подписания Дополнительного соглашения, Исполнитель вправе расторгнуть настоящий Договор в порядке, предусмотренном п.15.11 настоящего Договора.
|
||||
При оказании Услуг осуществлять взаимодействие с представителями Заказчика и доступ к оборудованию Заказчика, размещаемому на Технологической площадке для эксплуатационно-технического обслуживания в соответствии с Регламентом взаимодействия сторон в процессе оказания Услуг (Приложение №3 к настоящему Договору).
|
||||
Запрашивать у Заказчика информацию (материалы, документы и сведения технического и организационного характера), необходимую для качественного и бесперебойного оказания Услуг.
|
||||
По истечении 10 (десяти) календарных дней с момента приостановления оказания услуг или расторжения договора безвозвратно удалить все элементы информационной системы Заказчика, предоставляемые Исполнителем согласно Спецификации. Уведомление о приостановлении оказания услуг направляется в сроки, указанные в разделе 8 настоящего Договора. Уведомление о предстоящем расторжении договора в одностороннем порядке направляется в порядке, указанном в п.15.3. настоящего Договора.
|
||||
В случае нарушения условий п. 9.2.11 Договора, а также при выявлении недостоверной информации, предоставленной Заказчиком Исполнитель вправе в одностороннем порядке расторгнуть Договор без возмещения Заказчику каких-либо затрат. Исполнитель не несет ответственности за убытки Заказчика, возникшие в связи с таким расторжением.
|
||||
## Смирнов А.П. у Исполнителя в дополнение к предусмотренным в Спецификациях иные Инсталляционные, Абонентские (ежемесячные), Тарифицируемые и разовые (дополнительные) Услуги.
|
||||
## Морозов Е.В. у Исполнителя в дополнение к предусмотренным в Спецификациях иные Инсталляционные, Абонентские (ежемесячные), Тарифицируемые и разовые (дополнительные) Услуги.
|
||||
Отказаться от ранее заказанных Тарифицируемых Услуг, письменно уведомив о своем намерении Исполнителя не позднее, чем за пять рабочих дней до даты прекращения указанных услуг. При этом Заказчик обязан оплатить Исполнителю стоимость фактически оказанных услуг.
|
||||
Запрашивать у Исполнителя информацию о ходе выполнения Услуг.
|
||||
Требовать сверки взаиморасчетов по Договору.
|
||||
Осуществлять иные права по настоящему Договору.
|
||||
Контролировать процесс оказания Исполнителем Услуг по настоящему Договору, не вмешиваясь в производственную и хозяйственную деятельность Исполнителя.
|
||||
## Новиков В.Е. Заказчику Услуги в объеме и в сроки, предусмотренные настоящим Договором и Приложениями к нему.
|
||||
## Петров П.Е. Заказчику Услуги в объеме и в сроки, предусмотренные настоящим Договором и Приложениями к нему.
|
||||
Принять в целях размещения на Технологической площадке Исполнителя оборудование Заказчика по Акту приема-передачи оборудования, подписываемому уполномоченными представителями Сторон в порядке, предусмотренном Регламентом взаимодействия Сторон в процессе оказания Услуг, и обеспечить условия его размещения и сохранности в соответствии с условиями Договора и Соглашения об уровне обслуживания.
|
||||
Обеспечить работоспособность оборудования и программного обеспечения ПАК Исполнителя на Технологической площадке Исполнителя в соответствии с гарантиями и сертификатами их производителей на основании Соглашения об уровне обслуживания.
|
||||
Вести учет потребления и оплаты Заказчиком Услуг, оказываемых в соответствии со Спецификацией.
|
||||
@@ -49,7 +49,7 @@
|
||||
В случае возникновения аварий и их последствий на Технологической площадке обе Стороны составляют Акт, устанавливающий причины, виновника возникновения аварий, размеры и порядок возмещения ущерба.
|
||||
Обеспечивать представителям Заказчика возможность круглосуточного доступа к размещенному оборудованию Заказчика в соответствии с условиями настоящего Договора и Приложений к нему.
|
||||
|
||||
## Кузнецов А.И. принимать и оплачивать Услуги Исполнителя в размере и в сроки, установленные настоящим Договором.
|
||||
## Степанов А.В. принимать и оплачивать Услуги Исполнителя в размере и в сроки, установленные настоящим Договором.
|
||||
Предоставлять в согласованные сроки Исполнителю по его требованию все необходимые для оказания им Услуг материалы, документы и сведения технического и организационного характера.
|
||||
За свой счет доставить оборудование Заказчика в предварительно согласованные Сторонами сроки на Технологическую площадку Исполнителя, передать Исполнителю оборудование в порядке, предусмотренном Регламентом взаимодействия Сторон в процессе оказания Услуг, по Акту приема-передачи оборудования, подписываемому уполномоченными представителями Сторон, и обеспечить необходимые условия проверки его комплектации и работоспособности Исполнителем.
|
||||
Информировать Исполнителя о вносимых в документацию по обслуживанию оборудования дополнениях и изменениях не позднее 1 (одного) рабочего дня со дня внесения таких дополнений и изменений.
|
||||
@@ -135,7 +135,7 @@
|
||||
Заказчик имеет право на компенсацию в размере и порядке, установленном в пункте 2.3 Соглашения об уровне обслуживания.
|
||||
Уплата штрафных санкций не освобождает Стороны от выполнения обязательств по настоящему Договору.
|
||||
Каждая из Сторон Договора обязуется в течение срока действия настоящего Договора, а также в течение года с момента его расторжения/прекращения, воздерживаться от осуществления действий, направленных на переманивание работников другой Стороны.
|
||||
## Алексеев М.О. несет ответственность перед третьими лицами в случае предъявления любых претензий и исков такими третьими лицами, заключившими договоры с Заказчиком на оказание услуг, которые частично или полностью оказываются Заказчиком с помощью Услуг Исполнителя.
|
||||
## Новиков А.М. несет ответственность перед третьими лицами в случае предъявления любых претензий и исков такими третьими лицами, заключившими договоры с Заказчиком на оказание услуг, которые частично или полностью оказываются Заказчиком с помощью Услуг Исполнителя.
|
||||
Заказчик несет ответственность за соблюдение прав Исполнителя и третьих лиц на интеллектуальную собственность, исключительных прав, патентных, авторских, смежных или иных охраняемых законом прав. В случае, если к Исполнителю по вине Заказчика будут предъявлены со стороны третьих лиц какие-либо претензии, вытекающие из нарушения Заказчиком прав на интеллектуальную собственность, исключительных прав, патентных, авторских, смежных или иных охраняемых законом прав, Заказчик обязуется принять на себя эти претензии и возместить Исполнителю все убытки и расходы, понесенные Исполнителем в связи с нарушением таких прав, и за свой счет и на свой риск незамедлительно принять меры к урегулированию заявленных претензий.
|
||||
Заказчик полностью ответственен за сохранность своих учетных данных и за убытки или иной ущерб, которые могут возникнуть по причине несанкционированного использования этой информации. По факту утери, несанкционированного доступа к учетным данным или возможности возникновения такой ситуации Заказчик имеет право направить запрос Исполнителю на смену учетных данных. В этом случае Исполнитель по согласованию с Заказчиком осуществляет блокировку доступа к учетным данным Заказчика. Срок подобной блокировки согласовывается Сторонами дополнительно. При этом Исполнитель не несет ответственности за извещение любых третьих лиц о временной приостановке доступа Заказчика к его информационной системе и за возможные последствия, возникшие в результате отсутствия такого извещения.
|
||||
Заказчик несет ответственность за поддержание в актуальном состоянии списка его представителей, имеющих право обращаться в службу поддержки Исполнителя с запросами на изменение параметров Услуг.
|
||||
@@ -149,7 +149,7 @@
|
||||
Заказчик берет на себя обязательство:
|
||||
До заключения настоящего Договора письменно уведомить Исполнителя о любых обстоятельствах, прямо или косвенно связанных с криптовалютным майнингом, если такие обстоятельства могут повлиять на исполнение обязательств по Договору.
|
||||
Незамедлительно информировать Исполнителя о возникновении в течение срока действия Договора намерения использовать услуги в целях, указанных в п. 9.2.11 настоящего Договора.
|
||||
## Новиков А.П. не контролирует содержание информации, хранимой, публикуемой или распространяемой Заказчиком с использованием предоставленных Услуг, и не несет никакой ответственности за точность, качество и содержание такой информации.
|
||||
## Попов О.М. не контролирует содержание информации, хранимой, публикуемой или распространяемой Заказчиком с использованием предоставленных Услуг, и не несет никакой ответственности за точность, качество и содержание такой информации.
|
||||
Исполнитель не несет ответственность за нарушение Заказчиком прав третьих лиц, включая, но не ограничиваясь этим, нарушение Заказчиком прав на интеллектуальную собственность, исключительных прав, патентных, авторских, смежных или иных охраняемых законом прав, в том числе за нарушение, совершенное с использованием Услуг, предоставляемых Исполнителем.
|
||||
Исполнитель не несет ответственность за сбои в телекоммуникационных сетях, не находящихся под контролем Исполнителя в соответствии с Соглашением об уровне обслуживания.
|
||||
Исполнитель не несет ответственность за последствия изменений в размещаемом оборудовании и установленном на нем программном обеспечении, не согласованных с Исполнителем, и не гарантирует работоспособность ПАК Заказчика в случае внесения таких изменений Заказчиком.
|
||||
@@ -223,7 +223,7 @@
|
||||
Исполнитель не позднее двух календарных дней производит отключение оборудования Заказчика от сетевой инфраструктуры Исполнителя;
|
||||
демонтаж и вывоз оборудования Заказчика с Технологической площадки Исполнителя осуществляется Заказчиком самостоятельно в течение десяти календарных дней с даты окончания срока действия Договора, либо в иной согласованный Сторонами срок, оформленный в виде Дополнительного соглашения;
|
||||
отключение от электропитания и демонтаж стойки Заказчика по окончании срока действия настоящего Договора осуществляет Исполнитель, стоимость соответствующих услуг Исполнителя определяется, исходя из стоимости работ по деинсталляции инфраструктуры стойко-места, указанной в Спецификации. Заказчик обязуется подписать Дополнительное Соглашение на эти услуги и оплатить такие услуги Исполнителя в течение 5 (пять) рабочих дней с даты подписания Сторонами УПД и получения счета Исполнителя, но не позднее срока действия Договора;
|
||||
если Заказчик не оплатил стоимость Услуг Исполнителя по отключению от электропитания и демонтажу оборудования, или по истечении срока размещения оборудование Заказчика не было принято Заказчиком и не было вывезено Заказчиком в согласованный Сторонами срок, Исполнитель за свой счет складирует данное оборудование на условиях ответственного хранения на своей территории. В этом случае оборудование передается Заказчику только после оплаты Заказчиком расходов Исполнителя по отключению, демонтажу, складированию, хранению и приему-передаче оборудования. При этом стоимость Услуг Исполнителя по хранению оборудования определяется Дополнительном соглашении, исходя из расчета стоимости аренды склада на Технологической площадке Исполнителя. Заказчик обязуется оплатить такие услуги Исполнителя до момента передачи оборудования Заказчику. В момент возврата оборудования Морозов М.П. подписывается Акт приема-передачи оборудования с хранения в двух экземплярах.
|
||||
если Заказчик не оплатил стоимость Услуг Исполнителя по отключению от электропитания и демонтажу оборудования, или по истечении срока размещения оборудование Заказчика не было принято Заказчиком и не было вывезено Заказчиком в согласованный Сторонами срок, Исполнитель за свой счет складирует данное оборудование на условиях ответственного хранения на своей территории. В этом случае оборудование передается Заказчику только после оплаты Заказчиком расходов Исполнителя по отключению, демонтажу, складированию, хранению и приему-передаче оборудования. При этом стоимость Услуг Исполнителя по хранению оборудования определяется Дополнительном соглашении, исходя из расчета стоимости аренды склада на Технологической площадке Исполнителя. Заказчик обязуется оплатить такие услуги Исполнителя до момента передачи оборудования Заказчику. В момент возврата оборудования Кузнецов О.В. подписывается Акт приема-передачи оборудования с хранения в двух экземплярах.
|
||||
Никакое изменение, исправление, добавление или отмена любых положений настоящего Договора не вступает в силу, пока не будет согласовано в письменной форме уполномоченными представителями Исполнителя и Заказчика.
|
||||
Исполнитель вправе расторгнуть настоящий Договор в одностороннем порядке в случае отказа или уклонения Заказчика от подписания дополнительного соглашения об изменении цен по Договору (п.2.1.3) на условиях Исполнителя, направив Заказчику письменное уведомление не менее, чем за 10 (десять) рабочих дней до даты предполагаемого расторжения. В этом случае оплата оказанных Исполнителем услуг до даты расторжения осуществляется Заказчиком на прежних условиях.
|
||||
# ЗАКЛЮЧЕНИЕ ДОГОВОРА
|
||||
@@ -282,5 +282,5 @@
|
||||
|---|---|
|
||||
|
||||
|
||||
| Заказчик ЗАО «Меридиан» Юридический адрес: Генеральный директор _______________ /ФИО/ М.П. | Исполнитель ООО "ФИОЩЦ" Юридический адрес: 115404, г. Москва, Вн. Тер. Г. Муниципальный округ Бирюлево Восточное, ул. 1-я Стекольная, д.7 стр. 2 Почтовый адрес: 115404, г. Москва, ул. 1-я Стекольная, д.7с2 ИНН 9325731296, КПП 051543039 ОГРН 1094103489237 Р/с 40702435046811293176 АО «Стандарт», г. Москва Кор/сч 30101434381368067539 БИК: 044525225 e-mail bxkuno@company.local Web-site www.nubes.ru Тел. +7 (343) 986-75-93 Генеральный директор _______________ /В. С. Степаненко/ М.П. |
|
||||
| Заказчик ООО «Альянс» Юридический адрес: Генеральный директор _______________ /ВИП/ М.П. | Исполнитель ООО «Спектр» Юридический адрес: 115404, г. Москва, Вн. Тер. Г. Муниципальный округ Бирюлево Восточное, ул. 1-я Стекольная, д.7 стр. 2 Почтовый адрес: 115404, г. Москва, ул. 1-я Стекольная, д.7с2 ИНН 1846691249, КПП 350443068 ОГРН 1048672318430 Р/с 40702701822898587344 АО «Формат», г. Москва Кор/сч 30101201490272090211 БИК: 044525225 e-mail ypiorej@company.local Web-site www.nubes.ru Тел. +7 (495) 906-87-80 Генеральный директор _______________ /В. С. Степаненко/ М.П. |
|
||||
|---|---|
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
|
||||
г. Москва «27» февраля 2026
|
||||
|
||||
**ЗАО «Импульс»** именуемое в дальнейшем "Заказчик", в лице Директора ФИО, действующего на основании Устава, и **ООО **"**НУБЕС**", именуемое в дальнейшем "Исполнитель", в лице Генерального директора Лебедев Н.С., действующего на основании Устава, с другой стороны, заключили настоящее Дополнительное соглашение №1 (далее - Соглашение) к Договору №01300_2 от 29.12.2025 (далее - Договор) о нижеследующем:
|
||||
**АО «Синтез»** именуемое в дальнейшем "Заказчик", в лице Директора ФИО, действующего на основании Устава, и **ООО **"**НУБЕС**", именуемое в дальнейшем "Исполнитель", в лице Генерального директора Михайлов В.Н., действующего на основании Устава, с другой стороны, заключили настоящее Дополнительное соглашение №1 (далее - Соглашение) к Договору №01300_2 от 29.12.2025 (далее - Договор) о нижеследующем:
|
||||
**1. ПРЕДМЕТ ДОПОЛНИТЕЛЬНОГО СОГЛАШЕНИЯ**
|
||||
Руководствуясь п. 15.7, п.15.9 Договора, Стороны договорились о нижеследующем:
|
||||
Изменить Спецификацию и стоимость Услуг (Приложение №1 к Договору). Утвердить новую Спецификацию и стоимость Услуг в соответствии с Приложением №1 к настоящему Соглашению.
|
||||
@@ -33,7 +33,7 @@
|
||||
|
||||
|
||||
|
||||
| Заказчик ООО «Спектр» Юридический адрес: Почтовый адрес: ИНН , КПП ОГРН Р/с Кор/сч БИК: Тел. , e-mail Директор _______________ФИО М.П. | Исполнитель ООО «НУБЕС» Юридический адрес: 592106, ж. Нквзлч, Лв. Бъи. А. Ениефьзсшашъя жцбса Нцмяеэвз Лшлцурбзц, вж. 0-й Лахалфусщд, ц.9 юпо. 1 Почтовый адрес: 755298, д. Мцръьб, юм. 9-з Хщзддгэгтъ, д.7ъ9 ИНН 4115676360, КПП 761577138 ОГРН 1759258523572 Р/с 40702665883135798793 АО «Прогресс», г. Москва Кор/сч 30101181264373851255 БИК: 044525225 e-mail rlvti@example.ru Web-site www.nubes.ru Тел. +7 (812) 636-00-61 Генеральный директор _______________ / Смирнов С.Д./ М.П. |
|
||||
| Заказчик ООО «Импульс» Юридический адрес: Почтовый адрес: ИНН , КПП ОГРН Р/с Кор/сч БИК: Тел. , e-mail Директор _______________ФИО М.П. | Исполнитель ООО «Синтез» Юридический адрес: 136627, г. Езэхгъ, Оз. Сгю. В. Лицнбьстлэзло якерд Ыэстйнвл Цлифвнэбщ, ул. 5-т Ффднкомъщо, у.8 шгэ. 7 Почтовый адрес: 084810, б. Ввжзгд, гф. 6-в Фтпжыобнзщ, я.8с1 ИНН 3686281037, КПП 831943119 ОГРН 1475471132267 Р/с 40702719106800760870 АО «Импульс», г. Москва Кор/сч 30101659188332581128 БИК: 044525225 e-mail qifdckke@org.example.ru Web-site www.nubes.ru Тел. +7 (343) 365-60-01 Генеральный директор _______________ / Павлов В.С./ М.П. |
|
||||
|---|---|
|
||||
|
||||
|
||||
@@ -53,5 +53,5 @@
|
||||
| Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | 137 880,96 | - | |
|
||||
|
||||
|
||||
| Заказчик Директор ООО «Спектр» _______________/ФИО/ М.П. | Исполнитель Генеральный директор ООО "НУБЕС" _______________ /Смирнов С.Д./ М.П. |
|
||||
| Заказчик Директор ООО «Импульс» _______________/ФИО/ М.П. | Исполнитель Генеральный директор ООО «Прогресс» _______________ /Павлов В.С./ М.П. |
|
||||
|---|---|
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
Приложение № 1
|
||||
к Договору на оказание технологических услуг № 03700_1 от 01.02.2026 г.
|
||||
к Договору на оказание технологических услуг № 20847_0 от 01.02.2026 г.
|
||||
|
||||
|
||||
**Спецификация и стоимость услуг**
|
||||
@@ -20,7 +20,7 @@
|
||||
|
||||
|
||||
|
||||
| г. Москва | 01.02.2026г. |
|
||||
| с. Щйзьзф | 01.02.2026г. |
|
||||
|---|---|
|
||||
|
||||
|
||||
@@ -30,7 +30,7 @@
|
||||
| 2 | Аренда PDU: 3Ф 32А вертикальный | 2 511,17 | 3 | 7 533,51 | 01.04.2026 |
|
||||
| 3 | Аренда серверного шкафа: 42Ux600x1200 | 2 440,00 | 3 | 7 320,00 | 01.04.2026 |
|
||||
| 4 | Аренда порта без резерва, в составе: Скорость порта: 1 Гбит/с - 3 шт. | 4 575,00 | 1 | 4 575,00 | 01.04.2026 |
|
||||
| 5 | Предоставление 1 ОВ в кабеле ВОЛС: НУБЕС-М9 Эр с. Эануен ьч. Ичмсжюхгб т. 5 Чт е. Арюомп ус. 9м Рклшппкэиъ ж1 тхн. 3 | 18 300,00 | 4 | 73 200,00 | 01.04.2026 |
|
||||
| 5 | Предоставление 1 ОВ в кабеле ВОЛС: НУБЕС-М9 От с. Щйзьзф чт. Фкъяъзгра а. 2 До с. Щйзьзф иг. 8ц Лжчюсвхшбр б1 йук. 7 | 18 300,00 | 4 | 73 200,00 | 01.04.2026 |
|
||||
| 6 | Аренда публичной подсети: Длина префикса: /29 - 5 IPv4 адресов | 884,50 | 1 | 884,50 | 01.04.2026 |
|
||||
| 7 | Next Generation Cloud: AMD 2.8 ГГц, в составе: Количество vCPU: гарантированная доля 80% - 32 шт. Объем vRAM - 96 ГБайт Дисковое пространство: SSD - 2000 ГБайт | 34 050,20 | 1 | 34 050,20 | 01.04.2026 |
|
||||
| Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | 769 279,53 | - |
|
||||
@@ -42,11 +42,11 @@
|
||||
| 2 | Аренда PDU: 3Ф 32А вертикальный | 2 511,17 | 3 | 7 533,51 | 01.04.2026 |
|
||||
| 3 | Аренда серверного шкафа: 42Ux600x1200 | 2 440,00 | 3 | 7 320,00 | 01.04.2026 |
|
||||
| 4 | Аренда порта без резерва, в составе: Скорость порта: 1 Гбит/с - 3 шт. | 4 575,00 | 1 | 4 575,00 | 01.04.2026 |
|
||||
| 5 | Предоставление 1 ОВ в кабеле ВОЛС: НУБЕС-М9 Эр с. Эануен ьч. Ичмсжюхгб т. 5 Чт е. Арюомп ус. 9м Рклшппкэиъ ж1 тхн. 3 | 18 300,00 | 4 | 73 200,00 | 01.04.2026 |
|
||||
| 5 | Предоставление 1 ОВ в кабеле ВОЛС: НУБЕС-М9 От с. Щйзьзф чт. Фкъяъзгра а. 2 До с. Щйзьзф иг. 8ц Лжчюсвхшбр б1 йук. 7 | 18 300,00 | 4 | 73 200,00 | 01.04.2026 |
|
||||
| 6 | Аренда публичной подсети: Длина префикса: /29 - 5 IPv4 адресов | 884,50 | 1 | 884,50 | 01.04.2026 |
|
||||
| 7 | Next Generation Cloud: AMD 2.8 ГГц, в составе: Количество vCPU: гарантированная доля 80% - 32 шт. Объем vRAM - 96 ГБайт Дисковое пространство: SSD - 2000 ГБайт | 34 050,20 | 1 | 34 050,20 | 01.04.2026 |
|
||||
| Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | 877 563,21 | - |
|
||||
|
||||
|
||||
| Заказчик Генеральный директор ООО «Синтез» ________________ /ФИО/ М.П. | Исполнитель Генеральный директор ООО "НУБЕС" _______________ /В.С. Степаненко/ М.П. |
|
||||
| Заказчик Генеральный директор ООО «Сфера» ________________ /ФИО/ М.П. | Исполнитель Генеральный директор ЗАО «Гарант» _______________ /В.С. Степаненко/ М.П. |
|
||||
|---|---|
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
Приложение № 1
|
||||
к Договору на оказание технологических услуг
|
||||
№72987_6 от 74.68.7738 г.
|
||||
№84484_0 от 20.12.2025 г.
|
||||
|
||||
|
||||
**Спецификация и стоимость услуг**
|
||||
@@ -15,15 +15,15 @@
|
||||
|
||||
|
||||
|
||||
| л. Щцсмнэ | 92.50.1170в. |
|
||||
| г. Москва | 20.12.2025г. |
|
||||
|---|---|
|
||||
|
||||
|
||||
| № п/п | Наименование Абонентских услуг | Цена, руб. с НДС | Объем услуг | Сумма, руб. с НДС | Планируемая дата начала оказания услуг |
|
||||
|---|---|---|---|---|---|
|
||||
| 1 | Next Generation Cloud (AMD 4.0 ГГц), в составе: Количество vCPU - 10 шт. Период тарификации - месяц Объем vRAM - 10 ГБайт Период тарификации - месяц Дисковое пространство: Fast SSD - 100 ГБайт Период тарификации - месяц | 4 928,30 | 1 | 4 928,30 | 09.96.9732 |
|
||||
| 1 | Next Generation Cloud (AMD 4.0 ГГц), в составе: Количество vCPU - 10 шт. Период тарификации - месяц Объем vRAM - 10 ГБайт Период тарификации - месяц Дисковое пространство: Fast SSD - 100 ГБайт Период тарификации - месяц | 4 928,30 | 1 | 4 928,30 | 29.01.2026 |
|
||||
| Итого абонентский платеж в руб. с учетом НДС | Итого абонентский платеж в руб. с учетом НДС | Итого абонентский платеж в руб. с учетом НДС | Итого абонентский платеж в руб. с учетом НДС | 4 928,30 | - |
|
||||
|
||||
|
||||
| Заказчик Директор ЗАО «Технология» ________________ ФИО | Исполнитель Генеральный директор ЧЩЭ "ЩНРЬА" _______________ Петров П.С. Х.Л. |
|
||||
| Заказчик Директор ЗАО «Меридиан» ________________ ФИО | Исполнитель Генеральный директор ЗАО «Импульс» _______________ Фёдоров П.С. М.П. |
|
||||
|---|---|
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
Приложение № 1
|
||||
к Договору №77153_0 от 30.99.0061 г.
|
||||
к Договору №68396_3 от 01.02.2026 г.
|
||||
|
||||
|
||||
**Спецификация и стоимость услуг**
|
||||
@@ -14,15 +14,15 @@
|
||||
|
||||
|
||||
|
||||
| ц. Чистфб | 88.29.7250а. |
|
||||
| г. Москва | 01.02.2026г. |
|
||||
|---|---|
|
||||
|
||||
|
||||
| № п/п | Наименование услуг | Цена, руб. с НДС | Объем услуг | Сумма, руб. с НДС | Планируемая дата начала оказания услуг |
|
||||
|---|---|---|---|---|---|
|
||||
| 1 | Облачный диск Valo Cloud, в составе: Число пользователей - 300 шт. Период тарификации - месяц Дисковое пространство: Объем хранения - 6000 ГБайт Период тарификации - месяц | 68 700,00 | 1 | 68 700,00 | 30.99.0061 |
|
||||
| 1 | Облачный диск Valo Cloud, в составе: Число пользователей - 300 шт. Период тарификации - месяц Дисковое пространство: Объем хранения - 6000 ГБайт Период тарификации - месяц | 68 700,00 | 1 | 68 700,00 | 01.02.2026 |
|
||||
| Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | Итого абонентский платеж в руб с учетом НДС | 68 700,00 | - |
|
||||
|
||||
|
||||
| Заказчик Генеральный директор ЗАО «Альянс» ________________ ФИО. М.П. | Исполнитель Генеральный директор БУД "ЕЦКЫМ" _______________ Петров А.В. М.П. |
|
||||
| Заказчик Генеральный директор АО «Сфера» ________________ ФИО. М.П. | Исполнитель Генеральный директор АО «Сфера» _______________ Алексеев С.С. М.П. |
|
||||
|---|---|
|
||||
|
||||
+1
-1
@@ -20,7 +20,7 @@ if _sys_path_root not in sys.path:
|
||||
sys.path.insert(0, _sys_path_root)
|
||||
|
||||
# Версия приложения (меняется при изменениях)
|
||||
VERSION = "3.2.4"
|
||||
VERSION = "4.0.0"
|
||||
|
||||
|
||||
def create_app():
|
||||
|
||||
+25
-66
@@ -1,66 +1,25 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
width="120"
|
||||
height="120"
|
||||
id="svg2"
|
||||
version="1.1"
|
||||
inkscape:version="1.1 (c68e22c387, 2021-05-23)"
|
||||
sodipodi:docname="favicon.svg"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/">
|
||||
<defs
|
||||
id="defs4" />
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="5.6"
|
||||
inkscape:cx="91.428571"
|
||||
inkscape:cy="54.910714"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="layer1"
|
||||
showgrid="false"
|
||||
inkscape:window-width="1920"
|
||||
inkscape:window-height="1027"
|
||||
inkscape:window-x="-8"
|
||||
inkscape:window-y="-8"
|
||||
inkscape:window-maximized="1"
|
||||
fit-margin-top="0"
|
||||
fit-margin-left="0"
|
||||
fit-margin-right="0"
|
||||
fit-margin-bottom="0"
|
||||
inkscape:pagecheckerboard="0"
|
||||
width="120px" />
|
||||
<metadata
|
||||
id="metadata7">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Calque 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(-80.000001,-1018.2599)">
|
||||
<path
|
||||
style="fill:#004d00;stroke-width:0.100353;fill-opacity:1"
|
||||
d="m 144.12346,1127.3527 c -14.7384,-15.4935 -17.30029,-23.203 -14.91709,-44.8912 1.78418,-16.2372 1.43961,-18.7434 -3.2949,-23.9623 -4.60141,-5.0725 -4.72472,-5.8285 -0.95017,-5.8285 5.32989,0 5.67331,-6.0284 0.58406,-10.2519 -4.3155,-3.5819 -10.08626,-19.468 -8.64375,-23.7956 1.09412,-3.2824 21.29169,27.0158 23.93661,35.9068 0.94001,3.1601 8.83542,12.1943 17.54536,20.0767 11.55761,10.4589 14.47966,14.331 10.81518,14.331 -2.7616,0 -9.48553,-3.0338 -14.94204,-6.7417 -6.36215,-4.323 -10.81609,-5.8461 -12.41642,-4.2461 -1.60033,1.6005 3.29311,7.7342 13.64167,17.0989 8.87547,8.0322 15.48529,15.2553 14.68853,16.052 -0.79676,0.7967 -7.93147,-2.6984 -15.85488,-7.7667 -16.57177,-10.6009 -17.2489,-10.7849 -17.23587,-4.6824 0.0132,5.7346 7.77953,18.5635 16.5486,27.3327 3.71587,3.7157 6.75613,7.9746 6.75613,9.4643 0,5.5255 -6.27497,2.4016 -16.26102,-8.096 z"
|
||||
id="path3974"
|
||||
inkscape:connector-curvature="0" />
|
||||
</g>
|
||||
</svg>
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
|
||||
<!-- Creator: CorelDRAW -->
|
||||
<svg xmlns="http://www.w3.org/2000/svg" xml:space="preserve" width="82.3711mm" height="18.2443mm" version="1.1" style="shape-rendering:geometricPrecision; text-rendering:geometricPrecision; image-rendering:optimizeQuality; fill-rule:evenodd; clip-rule:evenodd"
|
||||
viewBox="0 0 8221.93 1821.07"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:xodm="http://www.corel.com/coreldraw/odm/2003">
|
||||
<defs>
|
||||
<style type="text/css">
|
||||
<![CDATA[
|
||||
.fil0 {fill:#001C34}
|
||||
]]>
|
||||
</style>
|
||||
</defs>
|
||||
<g id="Слой_x0020_1">
|
||||
<metadata id="CorelCorpID_0Corel-Layer"/>
|
||||
<g id="_2283355517888">
|
||||
<path class="fil0" d="M477.49 479.69l-413.51 0 -63.98 276.48 178.44 0 1.17 1028.71 0 26.75 0.03 0 276.39 0 0 -871.72c0,-101.28 82.43,-183.69 183.75,-183.69l589.25 3.44c101.34,0 183.76,82.46 183.76,183.74l0 871.72 276.44 0 0 -871.72c0,-253.77 -206.46,-460.15 -460.05,-460.15l-589.52 -3.53 -162.17 0.45 0 -0.48z"/>
|
||||
<path class="fil0" d="M6664.65 1813.37l1181.04 0c212.14,0 376.24,-175.01 376.24,-387.08 0,-212.13 -172.55,-384.68 -384.69,-384.68l-653.66 0c-60.22,0 -109.16,-48.94 -109.16,-109.18l0 -66.18c0,-60.19 48.94,-109.14 109.16,-109.14l695.76 0 63.74 -275.49 -759.5 0c-212.13,0 -384.66,172.53 -384.66,384.63l0 66.18c0,212.13 172.53,384.67 384.66,384.67l653.66 0c60.2,0 109.2,49 109.2,109.19 0,60.13 -49,116.1 -109.2,116.1l-1118.9 0 -53.68 270.98z"/>
|
||||
<path class="fil0" d="M6200.79 483.5l-723.21 0c-215.88,0 -391.47,175.6 -391.47,391.51l0 485.5c0,248.38 202.05,450.4 450.4,450.4l989.38 0 62.13 -268.51 -1051.51 0c-96.41,0 -174.95,-85.37 -174.95,-181.88l-1.5 -39.46 923.62 0 308.51 -1.84 0 -237.95 0 -206.26c0,-215.91 -175.59,-391.51 -391.41,-391.51zm115.96 560.28l-955.19 0 0 -168.77c0,-63.96 52.07,-116.05 116.02,-116.05l723.21 0c63.91,0 115.96,52.08 115.96,116.05l0 168.77z"/>
|
||||
<path class="fil0" d="M4683.49 1194.24l0 168.28c0,100.92 -81.7,178.37 -182.67,178.37l-589.87 1.23c-93.18,0 -170.28,-69.96 -181.63,-160.09l0 -458.13c11.36,-90.1 88.46,-160.07 181.63,-160.07l589.44 3.5c100.97,0 183.1,82.18 183.1,183.1l0 30.42 0 213.4zm-1230.2 -345.53l-0.89 -795.03 276.91 -53.68 0 526.07c55.74,-24.16 117.03,-37.74 181.5,-37.74l589.71 3.5c252.69,0 458.42,205.72 458.42,458.59l0 30.42 0 213.4 0 168.28c0,252.86 -205.73,458.54 -458.42,458.54l-589.71 -3.5c-252.7,0 -458.41,-205.67 -458.41,-458.56l0 -171.61 0 -240.48 0.89 -98.2z"/>
|
||||
<path class="fil0" d="M3041.25 1150.84l0 204.28c0,100.93 -82.15,183.05 -183.11,183.05l-582.11 -3.46c-100.96,0 -183.11,-82.16 -183.11,-183.08l0 -67.42 1.48 0.24 0 -862.65 -276.91 53.68 0.12 103.41 -0.12 0.04 0 772.69c0,252.87 205.72,458.54 458.39,458.54l582.4 3.5c252.67,0 458.4,-205.68 458.4,-458.55l0 -70.79 0.71 0.12 0 -862.65 -276.91 53.68 0.76 675.35z"/>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
||||
|
Before Width: | Height: | Size: 2.7 KiB After Width: | Height: | Size: 2.8 KiB |
Executable
+25
@@ -0,0 +1,25 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
|
||||
<!-- Creator: CorelDRAW -->
|
||||
<svg xmlns="http://www.w3.org/2000/svg" xml:space="preserve" width="82.3711mm" height="18.2443mm" version="1.1" style="shape-rendering:geometricPrecision; text-rendering:geometricPrecision; image-rendering:optimizeQuality; fill-rule:evenodd; clip-rule:evenodd"
|
||||
viewBox="0 0 8221.93 1821.07"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
xmlns:xodm="http://www.corel.com/coreldraw/odm/2003">
|
||||
<defs>
|
||||
<style type="text/css">
|
||||
<![CDATA[
|
||||
.fil0 {fill:#001C34}
|
||||
]]>
|
||||
</style>
|
||||
</defs>
|
||||
<g id="Слой_x0020_1">
|
||||
<metadata id="CorelCorpID_0Corel-Layer"/>
|
||||
<g id="_2283355517888">
|
||||
<path class="fil0" d="M477.49 479.69l-413.51 0 -63.98 276.48 178.44 0 1.17 1028.71 0 26.75 0.03 0 276.39 0 0 -871.72c0,-101.28 82.43,-183.69 183.75,-183.69l589.25 3.44c101.34,0 183.76,82.46 183.76,183.74l0 871.72 276.44 0 0 -871.72c0,-253.77 -206.46,-460.15 -460.05,-460.15l-589.52 -3.53 -162.17 0.45 0 -0.48z"/>
|
||||
<path class="fil0" d="M6664.65 1813.37l1181.04 0c212.14,0 376.24,-175.01 376.24,-387.08 0,-212.13 -172.55,-384.68 -384.69,-384.68l-653.66 0c-60.22,0 -109.16,-48.94 -109.16,-109.18l0 -66.18c0,-60.19 48.94,-109.14 109.16,-109.14l695.76 0 63.74 -275.49 -759.5 0c-212.13,0 -384.66,172.53 -384.66,384.63l0 66.18c0,212.13 172.53,384.67 384.66,384.67l653.66 0c60.2,0 109.2,49 109.2,109.19 0,60.13 -49,116.1 -109.2,116.1l-1118.9 0 -53.68 270.98z"/>
|
||||
<path class="fil0" d="M6200.79 483.5l-723.21 0c-215.88,0 -391.47,175.6 -391.47,391.51l0 485.5c0,248.38 202.05,450.4 450.4,450.4l989.38 0 62.13 -268.51 -1051.51 0c-96.41,0 -174.95,-85.37 -174.95,-181.88l-1.5 -39.46 923.62 0 308.51 -1.84 0 -237.95 0 -206.26c0,-215.91 -175.59,-391.51 -391.41,-391.51zm115.96 560.28l-955.19 0 0 -168.77c0,-63.96 52.07,-116.05 116.02,-116.05l723.21 0c63.91,0 115.96,52.08 115.96,116.05l0 168.77z"/>
|
||||
<path class="fil0" d="M4683.49 1194.24l0 168.28c0,100.92 -81.7,178.37 -182.67,178.37l-589.87 1.23c-93.18,0 -170.28,-69.96 -181.63,-160.09l0 -458.13c11.36,-90.1 88.46,-160.07 181.63,-160.07l589.44 3.5c100.97,0 183.1,82.18 183.1,183.1l0 30.42 0 213.4zm-1230.2 -345.53l-0.89 -795.03 276.91 -53.68 0 526.07c55.74,-24.16 117.03,-37.74 181.5,-37.74l589.71 3.5c252.69,0 458.42,205.72 458.42,458.59l0 30.42 0 213.4 0 168.28c0,252.86 -205.73,458.54 -458.42,458.54l-589.71 -3.5c-252.7,0 -458.41,-205.67 -458.41,-458.56l0 -171.61 0 -240.48 0.89 -98.2z"/>
|
||||
<path class="fil0" d="M3041.25 1150.84l0 204.28c0,100.93 -82.15,183.05 -183.11,183.05l-582.11 -3.46c-100.96,0 -183.11,-82.16 -183.11,-183.08l0 -67.42 1.48 0.24 0 -862.65 -276.91 53.68 0.12 103.41 -0.12 0.04 0 772.69c0,252.87 205.72,458.54 458.39,458.54l582.4 3.5c252.67,0 458.4,-205.68 458.4,-458.55l0 -70.79 0.71 0.12 0 -862.65 -276.91 53.68 0.76 675.35z"/>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 2.8 KiB |
+118
-188
@@ -11,108 +11,103 @@
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/jszip/3.10.1/jszip.min.js"></script>
|
||||
<style>
|
||||
:root {
|
||||
--bg: #f5f5f5;
|
||||
--brand-primary: #2563eb;
|
||||
--brand-gray: #d1d5db;
|
||||
--brand-grey-light: #f3f4f6;
|
||||
--bg: #f9fafb;
|
||||
--card: #ffffff;
|
||||
--border: #e0e0e0;
|
||||
--text: #1a1a1a;
|
||||
--muted: #888;
|
||||
--brand: #2563eb;
|
||||
--muted: #6b7280;
|
||||
--red: #ef4444;
|
||||
--green: #22c55e;
|
||||
}
|
||||
* { box-sizing: border-box; margin: 0; padding: 0; }
|
||||
body { font: 14px system-ui, sans-serif; color: var(--text); background: var(--bg); min-height: 100vh; }
|
||||
.topbar {
|
||||
background: var(--card); border-bottom: 1px solid var(--border);
|
||||
padding: 0 24px; height: 52px; display: flex; align-items: center; gap: 12px;
|
||||
font-weight: 600; font-size: 15px;
|
||||
background: var(--card); border-bottom: 1px solid var(--brand-gray);
|
||||
padding: 0 16px; height: 48px; display: flex; align-items: center; gap: 10px;
|
||||
}
|
||||
.content { max-width: 780px; margin: 28px auto; padding: 0 16px; }
|
||||
.topbar img { height: 18px; }
|
||||
.topbar .title { font-weight: 600; font-size: 14px; }
|
||||
.topbar .ver { font-weight: 400; color: var(--muted); font-size: 12px; margin-left: auto; }
|
||||
.content { max-width: 820px; margin: 20px auto; padding: 0 12px; }
|
||||
.card {
|
||||
background: var(--card); border-radius: 10px;
|
||||
border: 1px solid var(--border); box-shadow: 0 1px 3px rgba(0,0,0,.05);
|
||||
overflow: hidden;
|
||||
background: var(--card); border-radius: 12px;
|
||||
border: 1px solid var(--brand-gray); box-shadow: 0 1px 2px rgba(0,0,0,.04);
|
||||
}
|
||||
.card-header {
|
||||
background: #fafafa; padding: 10px 16px;
|
||||
font-weight: 600; font-size: 14px;
|
||||
border-bottom: 1px solid var(--border);
|
||||
}
|
||||
.card-body { padding: 16px; }
|
||||
|
||||
.file-input-wrap { margin-bottom: 12px; }
|
||||
.file-input-wrap input[type="file"] { width: 100%; font-size: 14px; }
|
||||
|
||||
.table-wrap {
|
||||
border: 1px solid var(--border); border-radius: 6px;
|
||||
overflow-y: auto; max-height: 60vh;
|
||||
background: var(--brand-grey-light); padding: 10px 12px;
|
||||
font-weight: 600; font-size: 14px; border-bottom: 1px solid var(--brand-gray);
|
||||
}
|
||||
.card-body { padding: 12px; }
|
||||
.sub { font-size: 12px; color: var(--muted); margin-bottom: 10px; line-height: 1.5; }
|
||||
.file-input-wrap { margin-bottom: 10px; }
|
||||
.file-input-wrap input[type="file"] { width: 100%; font-size: 13px; }
|
||||
.table-wrap { border: 1px solid var(--brand-gray); border-radius: 8px; overflow: hidden; }
|
||||
table { width: 100%; border-collapse: collapse; font-size: 13px; }
|
||||
th {
|
||||
background: #fafafa; text-transform: uppercase; padding: 6px 10px;
|
||||
border-right: 1px solid var(--border); text-align: left;
|
||||
font-weight: 600; font-size: 11px; color: var(--muted);
|
||||
background: var(--brand-grey-light); text-transform: uppercase; padding: 6px 8px;
|
||||
border-right: 1px solid var(--brand-gray); text-align: left;
|
||||
font-weight: 600; font-size: 10px; color: var(--muted);
|
||||
}
|
||||
td {
|
||||
padding: 6px 10px; border-right: 1px solid var(--border);
|
||||
border-bottom: 1px solid var(--border);
|
||||
padding: 5px 8px; border-right: 1px solid var(--brand-gray);
|
||||
border-bottom: 1px solid var(--brand-gray);
|
||||
}
|
||||
tr:hover td { background: rgba(37,99,235,.03); }
|
||||
.name-cell { max-width: 400px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
|
||||
.name-cell { max-width: 340px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
|
||||
.num-cell { text-align: right; white-space: nowrap; }
|
||||
.empty-row td { color: var(--muted); text-align: center; padding: 24px; }
|
||||
|
||||
.empty-row td { color: var(--muted); text-align: center; padding: 20px; }
|
||||
.remove-btn {
|
||||
cursor: pointer; color: #f87171; background: none; border: none;
|
||||
padding: 2px 6px; font-size: 15px; line-height: 1;
|
||||
padding: 2px 4px; font-size: 14px; line-height: 1;
|
||||
}
|
||||
.remove-btn:hover { color: var(--red); }
|
||||
|
||||
.footer-bar {
|
||||
margin-top: 12px; display: flex; justify-content: space-between; align-items: center;
|
||||
font-size: 13px; color: var(--muted);
|
||||
margin-top: 10px; display: flex; justify-content: space-between; align-items: center;
|
||||
font-size: 12px; color: var(--muted);
|
||||
}
|
||||
.btn {
|
||||
height: 34px; border-radius: 6px; padding: 0 16px; font-size: 13px;
|
||||
font-family: inherit; cursor: pointer; border: 1px solid var(--border);
|
||||
height: 32px; border-radius: 6px; padding: 0 12px; font-size: 13px;
|
||||
font-family: inherit; cursor: pointer; border: 1px solid var(--brand-gray);
|
||||
background: var(--card); color: var(--text);
|
||||
display: inline-flex; align-items: center; gap: 6px;
|
||||
display: inline-flex; align-items: center; gap: 5px;
|
||||
}
|
||||
.btn-primary { background: var(--brand); border-color: var(--brand); color: #fff; }
|
||||
.btn-primary { background: var(--brand-primary); border-color: var(--brand-primary); color: #fff; }
|
||||
.btn-primary:hover { opacity: .9; }
|
||||
.btn:disabled { opacity: .4; cursor: not-allowed; }
|
||||
|
||||
.status { margin-top: 12px; padding: 8px 12px; border-radius: 6px; font-size: 13px; display: none; }
|
||||
.status.success { background: #dcfce7; color: #166534; display: block; }
|
||||
.status.error { background: #fef2f2; color: #991b1b; display: block; }
|
||||
.status.info { background: #eff6ff; color: #1e40af; display: block; }
|
||||
.status { margin-top: 10px; padding: 8px 12px; border-radius: 8px; font-size: 13px; display: none; }
|
||||
.status.progress { background: #eff6ff; border: 1px solid var(--brand-primary); color: var(--brand-primary); display: block; }
|
||||
.status.done { background: #f0fdf4; border: 1px solid var(--green); color: #16a34a; display: block; }
|
||||
.status.error { background: #fef2f2; border: 1px solid var(--red); color: #991b1b; display: block; }
|
||||
.status.pack { background: #fefce8; border: 1px solid #eab308; color: #a16207; display: block; }
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div class="topbar">
|
||||
🛡️ DrHider — обфускация документов
|
||||
<span style="font-weight:400;color:var(--muted);font-size:12px;margin-left:auto;">v{{ version }}</span>
|
||||
<img src="/static/logo.svg" alt="Nubes">
|
||||
<span class="title">DrHider</span>
|
||||
<span class="ver">v{{ version }}</span>
|
||||
</div>
|
||||
|
||||
<div class="content">
|
||||
<div class="card">
|
||||
<div class="card-header">Выбор файлов</div>
|
||||
<div class="card-header">Обфускация документов</div>
|
||||
<div class="card-body">
|
||||
<p style="color:var(--muted);margin-bottom:12px;font-size:13px;">
|
||||
Загрузите документы (.docx, .xlsx, .pptx, .pdf, .txt).<br>
|
||||
DrHider заменит все персональные данные, реквизиты компаний, телефоны, email на фиктивные значения.
|
||||
<p class="sub">
|
||||
Загрузите документы (.docx, .pdf, .txt, .zip) — получите ZIP с обезличенными копиями.<br>
|
||||
Персональные данные, реквизиты, телефоны, email заменяются. CSV с таблицей замен сохраняется отдельно.
|
||||
</p>
|
||||
<div class="file-input-wrap">
|
||||
<input type="file" id="fileInput" multiple accept=".docx,.xlsx,.pptx,.pdf,.txt,.doc,.xls,.ppt">
|
||||
<input type="file" id="fileInput" multiple accept=".docx,.pdf,.txt,.doc,.zip">
|
||||
</div>
|
||||
<div class="table-wrap">
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Имя</th>
|
||||
<th style="width:90px;">Размер</th>
|
||||
<th style="width:90px;">Статус</th>
|
||||
<th style="width:40px;"></th>
|
||||
<th style="width:80px;">Размер</th>
|
||||
<th style="width:80px;">Статус</th>
|
||||
<th style="width:32px;"></th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody id="fileList">
|
||||
@@ -122,172 +117,107 @@
|
||||
</div>
|
||||
<div class="footer-bar">
|
||||
<span id="fileCount">0 файлов</span>
|
||||
<button class="btn btn-primary" id="uploadBtn" disabled onclick="uploadFiles()">
|
||||
🛡️ Обфусцировать
|
||||
</button>
|
||||
<button class="btn btn-primary" id="uploadBtn" disabled onclick="uploadFiles()">🛡️ Обфусцировать</button>
|
||||
</div>
|
||||
<div class="status" id="status"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script>
|
||||
const fileInput = document.getElementById('fileInput');
|
||||
const fileList = document.getElementById('fileList');
|
||||
const fileCount = document.getElementById('fileCount');
|
||||
const uploadBtn = document.getElementById('uploadBtn');
|
||||
const status = document.getElementById('status');
|
||||
let selectedFiles = [];
|
||||
const fi = document.getElementById('fileInput');
|
||||
const fl = document.getElementById('fileList');
|
||||
const fc = document.getElementById('fileCount');
|
||||
const ub = document.getElementById('uploadBtn');
|
||||
const st = document.getElementById('status');
|
||||
let sf = [];
|
||||
|
||||
function formatSize(bytes) {
|
||||
if (bytes < 1024) return bytes + ' B';
|
||||
if (bytes < 1024 * 1024) return (bytes / 1024).toFixed(1) + ' KB';
|
||||
return (bytes / (1024 * 1024)).toFixed(1) + ' MB';
|
||||
function fs(b) { return b < 1024 ? b + ' B' : b < 1048576 ? (b / 1024).toFixed(1) + ' KB' : (b / 1048576).toFixed(1) + ' MB'; }
|
||||
|
||||
function rr() {
|
||||
if (sf.length === 0) { fl.innerHTML = '<tr class="empty-row"><td colspan="4">Нет выбранных файлов</td></tr>'; }
|
||||
else { fl.innerHTML = sf.map((f, i) => '<tr id="row-' + i + '"><td class="name-cell">' + f.name + '</td><td class="num-cell">' + fs(f.size) + '</td><td class="num-cell" id="st-' + i + '" style="font-size:12px;">—</td><td><button class="remove-btn" onclick="rm(' + i + ')">✕</button></td></tr>').join(''); }
|
||||
fc.textContent = sf.length + ' файлов';
|
||||
ub.disabled = sf.length === 0;
|
||||
}
|
||||
|
||||
function renderFiles() {
|
||||
if (selectedFiles.length === 0) {
|
||||
fileList.innerHTML = '<tr class="empty-row"><td colspan="3">Нет выбранных файлов</td></tr>';
|
||||
} else {
|
||||
fileList.innerHTML = selectedFiles.map((f, i) =>
|
||||
'<tr id="row-' + i + '">' +
|
||||
'<td class="name-cell">' + f.name + '</td>' +
|
||||
'<td class="num-cell">' + formatSize(f.size) + '</td>' +
|
||||
'<td class="num-cell" id="status-' + i + '" style="font-size:12px;">—</td>' +
|
||||
'<td><button class="remove-btn" onclick="removeFile(' + i + ')">✕</button></td>' +
|
||||
'</tr>'
|
||||
).join('');
|
||||
}
|
||||
fileCount.textContent = selectedFiles.length + ' файлов';
|
||||
uploadBtn.disabled = selectedFiles.length === 0;
|
||||
function rm(i) { sf.splice(i, 1); const d = new DataTransfer(); sf.forEach(f => d.items.add(f)); fi.files = d.files; rr(); }
|
||||
|
||||
window.addEventListener('load', () => { sf = []; fi.value = ''; rr(); });
|
||||
fi.addEventListener('change', () => { sf = Array.from(fi.files); rr(); });
|
||||
|
||||
function ts() {
|
||||
const d = new Date();
|
||||
return d.getFullYear() + '-' + String(d.getMonth() + 1).padStart(2, '0') + '-' + String(d.getDate()).padStart(2, '0') + '_' + String(d.getHours()).padStart(2, '0') + '-' + String(d.getMinutes()).padStart(2, '0') + '-' + String(d.getSeconds()).padStart(2, '0');
|
||||
}
|
||||
|
||||
function removeFile(i) {
|
||||
selectedFiles.splice(i, 1);
|
||||
// Пересоздаём FileList через DataTransfer
|
||||
const dt = new DataTransfer();
|
||||
selectedFiles.forEach(f => dt.items.add(f));
|
||||
fileInput.files = dt.files;
|
||||
renderFiles();
|
||||
}
|
||||
|
||||
// Сброс при загрузке страницы
|
||||
window.addEventListener('load', () => {
|
||||
selectedFiles = [];
|
||||
fileInput.value = '';
|
||||
renderFiles();
|
||||
});
|
||||
|
||||
fileInput.addEventListener('change', () => {
|
||||
selectedFiles = Array.from(fileInput.files);
|
||||
renderFiles();
|
||||
});
|
||||
|
||||
function setStatus(idx, html) {
|
||||
const el = document.getElementById('status-' + idx);
|
||||
if (el) el.innerHTML = html;
|
||||
}
|
||||
function ss(idx, h) { const e = document.getElementById('st-' + idx); if (e) e.innerHTML = h; }
|
||||
|
||||
async function uploadFiles() {
|
||||
if (selectedFiles.length === 0) return;
|
||||
uploadBtn.disabled = true;
|
||||
|
||||
const total = selectedFiles.length;
|
||||
const results = []; // { name, blob } для JSZip
|
||||
if (sf.length === 0) return;
|
||||
ub.disabled = true;
|
||||
const total = sf.length;
|
||||
const tstamp = ts();
|
||||
const maps = [];
|
||||
const zip = new JSZip();
|
||||
let ok = 0, fail = 0;
|
||||
|
||||
for (let i = 0; i < total; i++) {
|
||||
const f = selectedFiles[i];
|
||||
const n = i + 1;
|
||||
|
||||
setStatus(i, '⏳');
|
||||
status.className = 'status info';
|
||||
status.textContent = 'Файл ' + n + '/' + total + ': ' + f.name;
|
||||
|
||||
const f = sf[i], n = i + 1;
|
||||
ss(i, '⏳');
|
||||
st.className = 'status progress';
|
||||
st.textContent = 'Файл ' + n + '/' + total + ': ' + f.name;
|
||||
const t0 = performance.now();
|
||||
const fd = new FormData();
|
||||
fd.append('files', f, f.name);
|
||||
|
||||
try {
|
||||
const blob = await new Promise((resolve, reject) => {
|
||||
const xhr = new XMLHttpRequest();
|
||||
xhr.open('POST', '/api/drhider');
|
||||
xhr.responseType = 'blob';
|
||||
xhr.timeout = 600000;
|
||||
|
||||
xhr.onload = () => {
|
||||
if (xhr.status === 200) resolve(xhr.response);
|
||||
else reject(new Error('Сервер ' + xhr.status));
|
||||
};
|
||||
xhr.onerror = () => reject(new Error('Сеть'));
|
||||
xhr.ontimeout = () => reject(new Error('Таймаут'));
|
||||
xhr.send(fd);
|
||||
const x = new XMLHttpRequest();
|
||||
x.open('POST', '/api/drhider');
|
||||
x.responseType = 'blob';
|
||||
x.timeout = 600000;
|
||||
x.onload = () => x.status === 200 ? resolve(x.response) : reject(new Error('Сервер ' + x.status));
|
||||
x.onerror = () => reject(new Error('Сеть'));
|
||||
x.ontimeout = () => reject(new Error('Таймаут'));
|
||||
x.send(fd);
|
||||
});
|
||||
|
||||
const elapsed = ((performance.now() - t0) / 1000).toFixed(1);
|
||||
setStatus(i, '<span style="color:#22c55e">✓ ' + elapsed + 'с</span>');
|
||||
results.push({ name: f.name, blob: blob });
|
||||
const el = ((performance.now() - t0) / 1000).toFixed(1);
|
||||
const iz = await JSZip.loadAsync(blob);
|
||||
const ks = Object.keys(iz.files).filter(k => !iz.files[k].dir);
|
||||
for (const k of ks) {
|
||||
const d = await iz.files[k].async('blob');
|
||||
if (k === 'mapping.csv') {
|
||||
const t = await iz.files[k].async('string');
|
||||
const ls = t.split('\n');
|
||||
maps.push(maps.length === 0 ? ls.join('\n') : ls.slice(1).join('\n'));
|
||||
} else { zip.file(k, d); }
|
||||
}
|
||||
ss(i, '<span style="color:#22c55e">✓ ' + el + 'с</span>');
|
||||
ok++;
|
||||
|
||||
} catch (err) {
|
||||
setStatus(i, '<span style="color:#ef4444">✗</span>');
|
||||
ss(i, '<span style="color:#ef4444">✗</span>');
|
||||
fail++;
|
||||
}
|
||||
|
||||
// Пауза между файлами
|
||||
if (i < total - 1) await new Promise(r => setTimeout(r, 300));
|
||||
}
|
||||
|
||||
// ── Упаковка в один ZIP ──
|
||||
if (results.length > 0) {
|
||||
status.className = 'status info';
|
||||
status.textContent = 'Упаковка в ZIP...';
|
||||
|
||||
const zip = new JSZip();
|
||||
for (const r of results) {
|
||||
// Извлекаем обфусцированный файл из ZIP-ответа бэкенда
|
||||
const innerZip = await JSZip.loadAsync(r.blob);
|
||||
const files = Object.keys(innerZip.files).filter(k => !k.startsWith('mapping') && !innerZip.files[k].dir);
|
||||
for (const name of files) {
|
||||
const data = await innerZip.files[name].async('blob');
|
||||
// Имя: оригинальное_имя_obfuscated.расширение
|
||||
const ext = name.split('.').pop();
|
||||
const base = r.name.replace(/\.[^.]+$/, '');
|
||||
zip.file(base + '_obfuscated.' + ext, data);
|
||||
}
|
||||
// mapping.csv — только один (из первого файла или объединить)
|
||||
if (innerZip.files['mapping.csv']) {
|
||||
const csv = await innerZip.files['mapping.csv'].async('string');
|
||||
const existing = zip.files['mapping.csv'];
|
||||
if (existing) {
|
||||
// Дописываем к существующему (кроме заголовка)
|
||||
const lines = csv.split('\n').slice(1).join('\n');
|
||||
zip.file('mapping.csv', (await existing.async('string')) + '\n' + lines);
|
||||
} else {
|
||||
zip.file('mapping.csv', csv);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const finalZip = await zip.generateAsync({ type: 'blob' });
|
||||
const url = URL.createObjectURL(finalZip);
|
||||
const a = document.createElement('a');
|
||||
a.href = url;
|
||||
a.download = 'drhider_output.zip';
|
||||
a.click();
|
||||
URL.revokeObjectURL(url);
|
||||
if (ok > 0) {
|
||||
st.className = 'status pack'; st.textContent = 'Упаковка...';
|
||||
const zb = await zip.generateAsync({ type: 'blob' });
|
||||
const u = URL.createObjectURL(zb);
|
||||
const a = document.createElement('a'); a.href = u; a.download = 'drhider_' + tstamp + '.zip'; a.click();
|
||||
URL.revokeObjectURL(u);
|
||||
}
|
||||
|
||||
// ── Итог ──
|
||||
if (fail === 0) {
|
||||
status.className = 'status success';
|
||||
status.textContent = '✅ Готово! ' + ok + '/' + total;
|
||||
} else {
|
||||
status.className = 'status error';
|
||||
status.textContent = 'Готово: ' + ok + ' OK, ' + fail + ' ошибок из ' + total;
|
||||
if (maps.length > 0) {
|
||||
const cb = new Blob(['\ufeff' + maps.join('\n')], { type: 'text/csv;charset=utf-8' });
|
||||
const u = URL.createObjectURL(cb);
|
||||
const a = document.createElement('a'); a.href = u; a.download = 'drhider_' + tstamp + '.csv'; a.click();
|
||||
URL.revokeObjectURL(u);
|
||||
}
|
||||
|
||||
uploadBtn.disabled = false;
|
||||
st.className = fail === 0 ? 'status done' : 'status error';
|
||||
st.textContent = fail === 0 ? '✅ Готово! ' + ok + '/' + total : 'Готово: ' + ok + ' OK, ' + fail + ' ошибок из ' + total;
|
||||
ub.disabled = false;
|
||||
}
|
||||
</script>
|
||||
</body>
|
||||
|
||||
Reference in New Issue
Block a user