Архитектура Vollständigkeit — Итоговое решение
Дата: 2026-06-30 Статус: ПРИНЯТО Основание: 3 архитектора провели дебаты → основатель выбрал гибридную модель
Контекст
Проблема: Как Lehrer узнаёт, кто из 25 родителей подписал, а кто нет — без классического Eltern-аккаунта с паролем?
Ограничения: - Никаких паролей для родителей - Никакой установки приложения - Data minimization (подпись — на устройстве) - Соло-фаундер, €0, IT=0, 4-8 недель на MVP - Рынок: DACH (DSGVO критичен)
Провал моделей A/B/C из дебатов: Все три модели предполагали персонализированную раздачу QR-кодов (каждому Schüler-у свой лист). В реальной школе это не работает: листочки раздают дежурные дети, они путаются, теряются, отдаются не тому. Один общий QR на класс — единственное, что выживает в Lehrerzimmer.
Принятая модель: Einmal-Registrierung + Device-Erkennung
Принцип
Родитель один раз (в начале Schuljahr или при первом Elternbrief) регистрируется через единый QR-код класса. Вводит имя Schüler-а, номер телефона, рисует подпись, подтверждает через SMS. Всё сохраняется в IndexedDB устройства.
Все последующие подписания: 5 секунд. QR → Face ID → подтвердить → подпись автоматом.
Фаза 1: Einmal-Registrierung (1 раз в год, 2 минуты)
``` УЧИТЕЛЬ: • Создаёт «Registrierungslink» для класса 5a • Получает ОДИН QR-код • Вешает в классе / рассылает в WhatsApp-группе / раздаёт на Elternabend
РОДИТЕЛЬ (первый раз): • Сканирует QR → открывается PWA • Экран 1: «Registrierung — Klasse 5a» ┌─────────────────────────────┐ │ Bitte registrieren Sie │ │ sich einmalig für die │ │ digitale Unterschrift. │ │ │ │ Name des Kindes: │ │ ┌─────────────────────┐ │ │ │ Max Mustermann │ │ │ └─────────────────────┘ │ │ │ │ Ihre Handynummer: │ │ ┌─────────────────────┐ │ │ │ +49 176 1234567 │ │ │ └─────────────────────┘ │ │ │ │ [Weiter] │ └─────────────────────────────┘
• Экран 2: «Ihre Unterschrift» ┌─────────────────────────────┐ │ Bitte hier unterschreiben: │ │ ┌─────────────────────┐ │ │ │ │ │ │ │ [Canvas] │ │ │ │ │ │ │ └─────────────────────┘ │ │ [Neu] [Fertig] │ └─────────────────────────────┘
• Экран 3: SMS-подтверждение ┌─────────────────────────────┐ │ Ein Code wurde an │ │ +49 176 ***567 gesendet. │ │ │ │ Code: ┌────────────┐ │ │ │ 4827 │ │ │ └────────────┘ │ │ │ │ [Bestätigen] │ └─────────────────────────────┘
• Экран 4: Готово ┌─────────────────────────────┐ │ ✅ Registrierung │ │ abgeschlossen! │ │ │ │ Max Mustermann │ │ Klasse 5a │ │ │ │ Ab jetzt: QR scannen → │ │ Gesicht zeigen → fertig. │ │ 5 Sekunden. │ └─────────────────────────────┘
УЧИТЕЛЬ получает уведомление: «Max Mustermann — Eltern registriert ✓» ```
Что сохраняется на устройстве родителя (IndexedDB):
- child_name: «Max Mustermann»
- schule_id: UUID школы
- signature_image: Canvas PNG (подпись)
- device_fingerprint: WebAuthn credential ID
- registration_token: серверный токен сессии
Что сохраняется на сервере:
- registration_id: UUID
- child_name: «Max Mustermann»
- phone_hash: SHA-256(+491761234567)
- device_fingerprint: credential ID
- klasse_id: привязка к классу
- status: «bestätigt»
- НЕ сохраняется: изображение подписи, номер телефона, IP, имя родителя
Фаза 2: Подписание (весь год, 1 секунда)
``` УЧИТЕЛЬ: • Создаёт Elternbrief «Klassenfahrt Leipzig» • Получает ОДИН QR-код на ВЕСЬ документ • Печатает → раздаёт → вешает в классе
РОДИТЕЛЬ: • Навёл камеру на QR → всё. • PWA открывается → проверяет IndexedDB → находит registration_token → отправляет на сервер → сервер фиксирует подпись → закрывается.
Родитель видит ТОЛЬКО зелёную галочку на 0.5 секунды: ┌─────────────────────────────┐ │ ✅ Unterschrieben! │ │ Max Mustermann │ │ Klassenfahrt Leipzig │ └─────────────────────────────┘
Экран исчезает сам через 1 секунду. Никаких кнопок. Никаких подтверждений. Навёл = подписал. ```
Почему без Face ID/PIN при каждом подписании: - Устройство уже идентифицировано при регистрации (credential ID + SMS) - Подпись уже сохранена в IndexedDB — вставляется автоматически - Для 95% школьных документов (Elternbrief, Einwilligung, Fotoerlaubnis) этого более чем достаточно - eIDAS SES (Simple Electronic Signature) не требует криптографической аутентификации при КАЖДОМ подписании — достаточно идентификации подписанта, которая произошла при регистрации
Опционально (для sensitive Dokumente): - Lehrer может включить «Face ID erforderlich» для конкретного Elternbrief - Тогда родитель: QR → Face ID → готово (2 секунды) - Например: Sorgerecht-документы, медицинские согласия
Что отправляется на сервер:
- registration_token → сервер знает, чей родитель подписал
- document_id
- credential_assertion (WebAuthn)
- timestamp
Что Lehrer видит в Dashboard:
┌──────────────────────────────────────────┐
│ 📋 Klassenfahrt Leipzig │
│ Klasse 5a • Frist: 04.07.2026 │
│ │
│ ████████████████░░░░░░ 72% (18/25) │
│ │
│ 🟢 Max Mustermann 30.06. 19:23 │
│ 🟢 Anna Schmidt 30.06. 17:05 │
│ 🟢 Leon Fischer 30.06. 18:41 │
│ 🔴 Paul Weber — │
│ 🔴 Emma Wagner — │
│ ... │
│ │
│ ⚡ 7 Eltern noch nicht unterschrieben. │
│ [Erinnerung senden] │
│ [Alle PDFs herunterladen] │
└──────────────────────────────────────────┘
Фаза 3: Смена устройства / потеря
``` РОДИТЕЛЬ (новый телефон / хочет добавить второй): • Сканирует тот же регистрационный QR класса • Вводит имя Schüler-а + номер телефона → SMS • Система видит: «Max Mustermann +49176... уже зарегистрирован» • Предлагает: «Neues Gerät hinzufügen?» • SMS-подтверждение → новое устройство привязано • Старое устройство продолжает работать (или отключается по желанию)
Поддерживается: мама + папа + бабушка = 3 устройства на одного Schüler-а. ```
Модель данных
```sql -- Таблица регистраций (одна запись на Schüler-а в год) CREATE TABLE registration ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), schule_id UUID NOT NULL, klasse_id UUID NOT NULL, child_name TEXT NOT NULL, -- «Max Mustermann» phone_hash TEXT NOT NULL, -- SHA-256(phone) device_fingerprint TEXT NOT NULL, -- WebAuthn credential ID status TEXT DEFAULT 'pending', -- pending|bestätigt|deaktiviert sms_verified_at TIMESTAMPTZ, created_at TIMESTAMPTZ DEFAULT NOW() );
-- Таблица устройств (может быть несколько на одну регистрацию) CREATE TABLE registered_device ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), registration_id UUID NOT NULL REFERENCES registration(id), credential_id TEXT NOT NULL, -- WebAuthn credential ID device_label TEXT, -- «Mamas iPhone» / «Papas Android» added_at TIMESTAMPTZ DEFAULT NOW(), last_used_at TIMESTAMPTZ );
-- Таблица подписаний (каждое подписание) CREATE TABLE signing_event ( id UUID PRIMARY KEY DEFAULT gen_random_uuid(), dokument_id UUID NOT NULL, registration_id UUID NOT NULL, -- кто подписал device_id UUID NOT NULL, -- с какого устройства credential_tail TEXT, -- 8 символов credential ID signed_at TIMESTAMPTZ DEFAULT NOW() );
-- Подпись (изображение) — ТОЛЬКО на устройстве родителя -- Сервер получает её ОДИН РАЗ при вставке в PDF и сразу удаляет из памяти ```
Где какие данные
| Данные | Сервер | Устройство Eltern | Обоснование |
|---|---|---|---|
| Имя Schüler-а | ✅ plaintext | ✅ | Необходимо для Vollständigkeit. Schule УЖЕ обрабатывает Klassenlisten |
| Номер телефона | ❌ hash only | — | Хеш для дедупликации. Полный номер — только в транзите SMS |
| Изображение подписи | ❌ (временная память при сборке PDF) | ✅ IndexedDB | Ключевое УТП: подпись не покидает устройство без необходимости |
| WebAuthn credential ID | ✅ | ✅ | Для привязки устройств |
| IP-адрес родителя | ❌ (hash, авто-null 30 дней) | — | Минимальный аудит |
| Статус подписания | ✅ | — | Функциональная необходимость |
SMS-верификация
Зачем: предотвращает регистрацию не-родителя (ребёнок сам регистрируется, посторонний). Даёт Lehrer-у Sicherheit: «это точно Eltern Макса».
Канал: любая дешёвая SMS (Twilio ~€0.05/SMS, или местный провайдер). Для пилота из 3 школ: 75 Schüler × 1-3 устройства = 75-225 SMS × €0.05 = €3.75-11.25.
Fallback если нет SMS: Lehrer вручную подтверждает регистрацию в Dashboard («Max Mustermann — я знаю этого родителя лично → подтвердить»). Это запасной вариант для Eltern ohne Handy / очень старых телефонов.
Что происходит с данными в конце Schuljahr
- Автоматическая архивация: все registration-записи помечаются
inactive - Lehrer получает уведомление: «Registrierungen für Klasse 5a werden am 31.07. archiviert. Eltern müssen sich im neuen Schuljahr neu registrieren.»
- Новый Schuljahr: Lehrer создаёт новый Registrierungslink для класса (уже 6a). Родители регистрируются заново за 2 минуты.
- Data minimization во времени: старые registration-записи удаляются через 12 месяцев после архивации.
Сравнение с моделями из дебатов
| Модель A (privacy) | Модель B (прагматик) | Модель C (эфемерно) | Принятая модель | |
|---|---|---|---|---|
| QR-кодов на класс | 25 уникальных | 25 уникальных | 25 уникальных | 1 общий |
| Раздача через детей | Хаос | Хаос | Хаос | Невозможно перепутать |
| Регистрация Eltern | Никогда | При каждом Elternbrief (ввод контактов) | При каждом Elternbrief | 1 раз в год |
| Время подписания | 30 сек | 15 сек | 15 сек | 1 сек |
| Подпись рисуется | Каждый раз | Каждый раз | Каждый раз | 1 раз |
| Сервер знает имя Schüler-а | ❌ (encrypted blob) | ✅ | ✅ (label) | ✅ |
| Сервер знает телефон Eltern | ❌ | ✅ (encrypted) | ⚠️ (эфемерно) | ❌ (только хеш) |
| SMS-верификация | ❌ | ❌ | ❌ | ✅ |
| Смена устройства | Сложно (wrapKey) | Невозможно | Невозможно | SMS-повтор |
| Риск «ребёнок сам подписал» | Высокий | Высокий | Средний | Низкий (SMS) |
Эволюционный план реализации
``` W1-W4 Validation: CustDev — спросить Lehrer-ов: «Готовы ли Eltern зарегистрироваться один раз через SMS?» «Есть ли Eltern ohne Handy? Сколько?»
W5-W7 MVP Core: • Таблица registration + registered_device • PWA: экран регистрации (имя + телефон + подпись + SMS) • PWA: экран подписания (Face ID → авто-подпись) • Lehrer-Dashboard: статусы Schüler (зелёные/красные) • WebAuthn-челлендж + credential storage
W8 MVP Complete: • SMS-провайдер (Twilio EU) • Ручное подтверждение Lehrer (fallback без SMS) • Auto-Erinnerung через WhatsApp (шаблон)
W9-W10 Polish: • Multi-Device: мама + папа + бабушка • Кнопка «Neues Gerät hinzufügen» • Авто-архивация в конце Schuljahr
W11-W12 Launch: • 3 пилотные школы • Сбор метрик: completion rate, время до 100%, NPS Lehrer + Eltern ```
Открытые вопросы (на CustDev и Rechtsgutachten)
- SMS-верификация и DSGVO: нужно ли согласие Eltern на получение SMS? (вероятно, да — через Datenschutzerklärung на экране регистрации)
- Хеш телефона — Personenbezug? SHA-256(+49176...) — псевдонимизация. Признаёт ли DSB это достаточной мерой?
- Минимальный возраст для регистрации: может ли Schüler сам зарегистрироваться? (SMS частично решает — нужен доступ к телефону Eltern)
- Eltern ohne Handy: сколько в реальности? Какая доля потребует бумажный fallback?
- Telegram вместо SMS? Telegram Bot API бесплатен и не требует номера телефона Eltern. Но требует Telegram-аккаунт у родителя. Проверить на CustDev.
Дебаты архитекторов: 2026-06-30. Модель принята основателем: 2026-06-30.