feat: живой цикл M2M с НРД + мастер установки ключа на флешку
Инфраструктура M2M (живой обмен с НРД через ИШ): - обработка M2MTransferResponse: ERROR(M2Mxx) → заявка Отклонена, сохранение ответа; INFO → ждём Decision; идемпотентность поллера - fallback-корреляция ответов с нулевым GUID (M2M14/M2M17) по FIFO - сырой XML ответа НРД в карточке заявки (для пересылки в ТП) - тестовый пакет роботу приведён к эталону m2m_robot_samples (CostInfo=Yes, 4 бумаги, IsolationStatus, DocumentSeries=сценарий); override паспорта - редирект из теста сразу в карточку заявки Мастер установки ключа Валидаты на флешку (admin/setup/keywizard): - пошаговый: загрузка .7z+пароль → выбор флешки → запись → справочник сертификатов (CRL) → перезапуск+проверка ИШ → готово - привилегированный воркер (bj-keymedia) в host-namespace через файл-обмен, bj-server остаётся в песочнице - сохранение структуры профиля архива (spr<N>), перечисление съёмных USB Прочее: - пакет-доказательство для ТП НРД + форма регистрации участника M2M - эталонные образцы робота (DOC/m2m_robot_samples) Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -26,10 +26,30 @@ type Settings struct {
|
||||
LK LKSettings `json:"lk"`
|
||||
CACerts CACertsSettings `json:"ca_certs"`
|
||||
News NewsSettings `json:"news"`
|
||||
Update UpdateSettings `json:"update"`
|
||||
License LicenseSettings `json:"license"`
|
||||
LastTest *TestRunResult `json:"last_test,omitempty"`
|
||||
UpdatedAt time.Time `json:"updated_at"`
|
||||
}
|
||||
|
||||
// LicenseSettings — лицензионный ключ (подписанный токен).
|
||||
type LicenseSettings struct {
|
||||
Key string `json:"key"` // компактный токен payload.signature.keyid
|
||||
PublicKey string `json:"public_key"` // base64 (если не зашит в бинарь)
|
||||
}
|
||||
|
||||
// UpdateSettings — авто-обновления из артефактории (#18/#20).
|
||||
type UpdateSettings struct {
|
||||
BaseURL string `json:"base_url"` // https://updates.example.com
|
||||
Channel string `json:"channel"` // "stable" | "beta"
|
||||
PublicKey string `json:"public_key"` // base64 Ed25519 (если не зашит в бинарь)
|
||||
AutoCheck bool `json:"auto_check"` // проверять автоматически
|
||||
LastCheck time.Time `json:"last_check"` // когда последний раз проверяли
|
||||
LastResult string `json:"last_result"` // текст результата проверки
|
||||
Available string `json:"available_version"` // доступная версия (если новее)
|
||||
Notes string `json:"notes,omitempty"` // заметки доступного релиза
|
||||
}
|
||||
|
||||
// NewsSettings — лента новостей (события системы, окна техработ, обновления
|
||||
// документации НРД). События добавляются вручную через UI или автоматически
|
||||
// doc-watcher'ом и cron-задачами. Каждое событие может быть скрыто (Dismissed)
|
||||
@@ -64,8 +84,7 @@ type DocSource struct {
|
||||
|
||||
// CACertsSettings — URL'ы для авто-загрузки сертификатов УЦ НРД и нашего
|
||||
// УЦ. Список редактируется пользователем; раз в сутки фоновая горутина
|
||||
// перекачивает каждый URL и переустанавливает сертификат, если он
|
||||
// поменялся. Все сертификаты идут в mroot/uRoot хранилища КриптоПро.
|
||||
// перекачивает каждый URL и сохраняет сертификат, если он поменялся.
|
||||
type CACertsSettings struct {
|
||||
URLs []string `json:"urls"`
|
||||
AutoUpdate bool `json:"auto_update"`
|
||||
@@ -91,12 +110,12 @@ type PostgresSettings struct {
|
||||
DSN string `json:"dsn"`
|
||||
}
|
||||
|
||||
// CryptoSettings — путь к JCP, провайдер, лицензионный ключ.
|
||||
// CryptoSettings — путь к PKCS#11 модулю и тип провайдера.
|
||||
type CryptoSettings struct {
|
||||
Provider string `json:"provider"` // "stub" | "cryptopro" | "validata" | "vipnet"
|
||||
Provider string `json:"provider"` // "stub" | "validata"
|
||||
SocketPath string `json:"socket_path"` // UDS crypto-service
|
||||
JCPPath string `json:"jcp_path"` // путь до jcp.jar
|
||||
LicenseKey string `json:"license_key"` // лицензионный ключ КриптоПро
|
||||
ModulePath string `json:"module_path"` // путь до .so модуля PKCS#11
|
||||
Profile string `json:"profile"` // активный профиль Валидаты (имя из pki1.conf)
|
||||
}
|
||||
|
||||
// NSDSettings — профиль и подключение к ИШ НРД.
|
||||
@@ -104,6 +123,12 @@ type NSDSettings struct {
|
||||
Profile string `json:"profile"` // "guest-gost", "test3-gost", ...
|
||||
IGWBaseURL string `json:"igw_base_url"` // http://host:port
|
||||
KeyContainer string `json:"key_container"` // имя контейнера (на стороне ИШ)
|
||||
|
||||
// Депозитарные реквизиты клиента — откуда списываются бумаги
|
||||
// (SettlementLocation в M2MTransferRequest). Из договора/письма НРД.
|
||||
DeponentCode string `json:"deponent_code"` // депкод, напр. MC0413600000
|
||||
AccountID string `json:"account_id"` // депозитарный счёт
|
||||
SectionID string `json:"section_id"` // раздел депозитарного счёта
|
||||
}
|
||||
|
||||
// LKSettings — настройки callback в ЛК клиента.
|
||||
@@ -165,6 +190,24 @@ func (r *RuntimeConfig) UpdatePostgres(s PostgresSettings) error {
|
||||
return r.save()
|
||||
}
|
||||
|
||||
// SaveLicense сохраняет лицензионные настройки.
|
||||
func (r *RuntimeConfig) SaveLicense(s LicenseSettings) error {
|
||||
r.mu.Lock()
|
||||
r.data.License = s
|
||||
r.data.UpdatedAt = time.Now().UTC()
|
||||
r.mu.Unlock()
|
||||
return r.save()
|
||||
}
|
||||
|
||||
// SaveUpdateSettings сохраняет настройки авто-обновлений.
|
||||
func (r *RuntimeConfig) SaveUpdateSettings(s UpdateSettings) error {
|
||||
r.mu.Lock()
|
||||
r.data.Update = s
|
||||
r.data.UpdatedAt = time.Now().UTC()
|
||||
r.mu.Unlock()
|
||||
return r.save()
|
||||
}
|
||||
|
||||
// UpdateCrypto сохраняет crypto-настройки.
|
||||
func (r *RuntimeConfig) UpdateCrypto(s CryptoSettings) error {
|
||||
r.mu.Lock()
|
||||
@@ -307,7 +350,7 @@ func (r *RuntimeConfig) ReadinessSummary() []Readiness {
|
||||
},
|
||||
{
|
||||
Name: "crypto-service",
|
||||
Configured: s.Crypto.Provider != "" && s.Crypto.Provider != "stub" && s.Crypto.JCPPath != "",
|
||||
Configured: s.Crypto.Provider != "" && s.Crypto.Provider != "stub",
|
||||
Ready: false,
|
||||
Message: cryptoMsg(s.Crypto),
|
||||
},
|
||||
@@ -336,15 +379,12 @@ func posMsg(dsn string) string {
|
||||
|
||||
func cryptoMsg(c CryptoSettings) string {
|
||||
if c.Provider == "" || c.Provider == "stub" {
|
||||
return "Криптография не настроена (provider=stub). КриптоПро JCP не подключён."
|
||||
return "Криптография не настроена (provider=stub) — реальная подпись недоступна."
|
||||
}
|
||||
if c.JCPPath == "" {
|
||||
return "Провайдер " + c.Provider + ", но путь к JCP не задан."
|
||||
if c.ModulePath == "" {
|
||||
return "Провайдер " + c.Provider + ", путь к PKCS#11 модулю не задан."
|
||||
}
|
||||
if c.LicenseKey == "" {
|
||||
return "Провайдер " + c.Provider + ", JCP есть, лицензия не введена."
|
||||
}
|
||||
return "Провайдер " + c.Provider + ", JCP подключён, лицензия введена."
|
||||
return "Провайдер " + c.Provider + ", PKCS#11 модуль: " + c.ModulePath
|
||||
}
|
||||
|
||||
func nsdMsg(n NSDSettings) string {
|
||||
|
||||
Reference in New Issue
Block a user