Compare commits

..

2305 Commits

Author SHA1 Message Date
ant b84b02f1b4 Merge pull request 'sync-arch: parser2 ^1.2.0 + прокидывание block_time из ActionEvent/DeltaEvent [C28-13]' (#92) from parser2-block-time-and-version into parser2
Typecheck / desktop (pull_request) Successful in 12m46s
Typecheck / controller (pull_request) Successful in 12m28s
Reviewed-on: #92
Reviewed-by: Алексей Муравьев <chairman.voskhod@gmail.com>
2026-06-05 10:45:08 +00:00
coopops c33ec53230 [C28-13][@ant] feat(controller): parser2 ^1.2.0 + прокидывание block_time из ActionEvent/DeltaEvent
- @coopenomics/parser2: "1.1.0" → "^1.2.0" — снят точный pin, апгрейд парсера = npm install
- IAction/IDelta: + block_time?: string (ISO-8601, parser1 не давал, parser2 1.2.0 отдаёт)
- parser2-event.mapper.ts: пробрасывает event.block_time в IAction.block_time и IDelta.block_time
- mapper.test: 2 новых проверки на block_time (delta + action) — 9/9 зелёные

Поверх ветки parser2 (#68). Native-delta остаётся явно проигнорированной (как у parser1), это отдельное расширение интерфейса при необходимости.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-06-05 08:05:31 +00:00
ant 7dcca3a2ae Merge pull request 'Эпик 4 sync-arch: правильная обработка форков блокчейна (релиз 1.1.2) [C28-14]' (#54) from parser2-epic-4-forks into parser2
Typecheck / desktop (pull_request) Successful in 13m20s
Typecheck / controller (pull_request) Successful in 13m21s
Reviewed-on: #54
Reviewed-by: Алексей Муравьев <chairman.voskhod@gmail.com>
2026-06-03 08:32:46 +00:00
ant 70752b2caa Merge pull request 'sync-arch: явные ошибки при unknown contract version / status (Story 6.5) [C28-16]' (#57) from parser2-epic-6-canonical-storage into parser2-epic-4-forks
Reviewed-on: #57
Reviewed-by: Алексей Муравьев <chairman.voskhod@gmail.com>
2026-06-03 08:31:35 +00:00
coopops 8c5568bcf8 [C28-16][@ant] revert: откат Story 6.1 (namespace bc + replaceBc) + Story 6.2 (signedDocumentFields) — вынос за MVP-релиз parser2
Цель релиза 1.1.2 — «затащить parser2 нормально», т.е. заменить транспорт parser1→parser2.
Эпик 6 «единый порядок хранения данных» — отдельная архитектурная санитация, не связана с
заменой транспорта. Включение её в MVP-релиз привнесло инвазивные изменения:

- Story 6.1 (namespace `db`/`bc` + `replaceBc` + переписанный ProjectDomainEntity) вводит
  двойной стандарт: одна entity на новом паттерне, 21 entity на старом. Потребители
  читают `project.master` (плоский флэт) — частичная миграция создаёт регрессии у resolver'ов.
  Полная миграция = большой blast radius на 22 entity + Epic 9.5 backlog. Откладывается
  в отдельный sync-arch sanitation-эпик.

- Story 6.2 (declarative `signedDocumentFields` + `normalizeSignedDocuments` + path-parser)
  — DRY-рефакторинг без функциональной выгоды. AppendixDeltaMapper и так руками вызывал
  `convertChainDocumentToDomainFormat`. Польза появится когда подписанных полей станет
  много — пока их одно поле в одной точке.

Остаётся: Story 6.5 (UnsupportedContractVersionError + auditUnknownStatus +
`BLOCKCHAIN_UNSUPPORTED_VERSION_STRICT`). Очевидный фикс silent loss при schema drift,
не инвазивный.

Удалено: composite-entity.contract.test.ts, signed-document-normalization.test.ts,
delta-mapper-signed-doc.contract.test.ts. CLAUDE.md секция Composite-Entity ADR-008
помечена как «будущая цель, не сейчас».

10 jest blockchain unit suites / 64 tests зелёные. tsc зелёный.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-06-02 10:37:48 +00:00
coopops 30b79ad1f7 [C28-16][@ant] revert: откат Story 6.3 (zod) + 6.4 (_checksum) — pre-mature и за гранью sync-слоя
Story 6.3 (per-doc-type zod schemas): валидация `signatures.length === 1/2` зашивала
документную семантику в нормализатор parser-event. Число и валидность подписей — домен
контракта (`require_auth`), не бэкенда. При расширении доктайпов контракта (1→2 подписи)
sync падал бы на структурно-валидной цепи. Структурный transform `meta: JSON-string → object`
(Story 6.2) остаётся.

Story 6.4 (`_checksum` колонка + sha256(canonical-json(bc))): потребитель — Epic 7 nightly
snapshot и Epic 8 reconciliation — ещё не реализованы. Колонка хранила бы пустую нагрузку
+ +20% storage + лишний sha256 на каждом save/update. Принцип «не добавлять контрольных
полей до появления потребителя». Алгоритм canonicalStringify заведём как часть Epic 8.

Удалено: src/shared/sync/{checksum.util.ts, signed-document-schemas.ts} + 3 теста +
applyBcChecksum + колонка _checksum + поле _checksum на BaseDomainEntity. Story 6.1
(namespace db/bc + replaceBc), 6.2 (declarative signedDocumentFields + meta transform),
6.5 (UnsupportedContractVersionError + auditUnknownStatus) сохраняются.

13 jest blockchain unit suites / 196 tests зелёные. tsc зелёный.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-06-02 08:37:57 +00:00
coopops 87747d1782 [C28-16][@ant] feat: UnsupportedContractVersionError + auditUnknownStatus — Story 6.5
Новые shared/sync/errors:
- UnsupportedContractVersionError(entityName, ctx{contract,table,primary_key,
  block_num}) — носит контекст для DLQ-операторской диагностики.
- auditUnknownStatus(entityName, receivedStatus, logger, allowedStatuses?) —
  фиксирует unknown-status drift в audit-trail с ожидаемыми вариантами.

AbstractEntitySyncService.processDelta: mapper вернул null → logger.error
("UNSUPPORTED_CONTRACT_VERSION", ctx) ВСЕГДА (раньше был silent warn). В strict-mode
(config.blockchain.unsupported_version_strict=true) дополнительно throw — парсер не
ACK'нет дельту, DLQ сработает. UnsupportedContractVersionError из try/catch
пробрасывается дальше; остальные ошибки по-прежнему логируются и return null.

config.ts: BLOCKCHAIN_UNSUPPORTED_VERSION_STRICT (default false) → blockchain
.unsupported_version_strict. Default false — не ломать прод немедленно;
включается на стенде после подтверждения отсутствия schema drift.

ProjectDomainEntity.mapStatusToDomain эталонно — default ветка вместо silent
UNDEFINED-возврата вызывает auditUnknownStatus с полным списком ожидаемых:
[pending,active,voting,result,finalized,cancelled]. Остальные mapStatusToDomain
(state, vote, segment, debt и т.д.) — Epic 9.5.

unsupported-version-explicit-error.test.ts (6) — UnsupportedContractVersionError
конструктор/контекст; auditUnknownStatus с/без allowedStatuses;
processDelta non-strict (logger.error + null), strict (throw),
happy-path (handleSyncDelta вызывается).

229/229 blockchain unit зелёные.

Эпик 6 закрыт целиком: 6.1 namespace, 6.2 normalizeSignedDocuments, 6.3 Zod schemas,
6.4 checksum, 6.5 explicit errors. Release 1.1.2 движется.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-06-02 07:52:40 +00:00
coopops f7a182e51f [C28-16][@ant] feat: detrministic _checksum sha256(bc canonical-json) — Story 6.4
checksum.util.ts: canonicalStringify(value) (рекурсивная сортировка ключей объектов,
порядок массивов сохраняется, bigint → string, undefined → "null"); computeBcChecksum
→ sha256-hex 64 chars от canonical-stringified bc-namespace. Без внешних зависимостей.

BaseTypeormEntity получает колонку `_checksum varchar(64) nullable` —
legacy записи без bc-namespace получают хэш от "null" (стабильно, но не несёт
информации); после миграции Epic 9.5 на namespace все блокчейн-зеркала получат
содержательный checksum. BaseDomainEntity получает поле `_checksum?: string | null`.

BaseBlockchainRepository.save и .update вызывают protected applyBcChecksum(domain,
typeormEntity) ПОСЛЕ mapper.toEntity и ДО repository.save — proseться через единую
точку, не лезем в 22 mapper'а. Поле bc-namespace → reconciliation Epic 8.2
сравнивает только то, что реально в цепи (локальные db-поля типа matrix_room_id
из цепи не получаются и в checksum их быть не должно).

checksum.util.test.ts (14) — canonicalStringify: primitives/array/nested/bigint/sort;
computeBcChecksum: 64 hex chars / детерминизм / change-detection / null-stable /
порядок массивов / контрольный фиксированный хэш на nested-структуре (catch для
несовместимого изменения алгоритма).

base-repo-checksum.contract.test.ts (3) — bc заданный → checksum по нему;
bc undefined → checksum от null; повторный вызов → одинаковый _checksum.

223/223 blockchain unit зелёные.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-06-02 07:44:55 +00:00
coopops 9774abb296 [C28-16][@ant] feat: Zod per-doc-type schemas + valid-pre-transform — Story 6.3
Новый файл shared/sync/signed-document-schemas.ts: signatureInfoSchema (ISignatureInfo)
+ три per-doc-type схемы IChainDocument2:
- chainDocumentSchema — default ≥1 подпись (стандартный мультисиг кооператива).
- singleSignatureChainDocumentSchema — ровно 1 (одиночный автор).
- twoSignatureChainDocumentSchema — ровно 2 (двухподписные акты signsupp/signchair
  и signact1/signact2; OQ-13: ВСЕ подписанты массивом, primary не выделяется).

SignedDocField (Story 6.2) расширен optional schema?: ZodTypeAny — backward-compat
для legacy полей без валидации. AbstractBlockchainDeltaMapper.normalizeSignedDocuments
делает schema.parse ДО transform: при schema-drift цепи (новая структура IChainDocument2
из коопконтракта) — Zod бросает ZodError, mapper.try/catch отдаёт null + warn, Story 6.5
повысит до alert. До этого PR drift молча проходил, meta оставался JSON-строкой.

Эталон: appendix-delta.mapper.ts — добавлен singleSignatureChainDocumentSchema
(приложение к ТЭМ имеет одного автора).

signed-document-schemas.test.ts (16) — каждая схема: valid → ok, обязательные поля
отсутствуют → fail, неверное число подписей → fail. signed-document-normalization
расширен 3 тестами на schema-pre-transform: валидная schema → нормализация проходит,
single-signature на 2 подписи → ZodError, missing hash → ZodError + meta не обновлена
(transform не вызвался).

206/206 blockchain unit зелёные.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-06-02 07:27:00 +00:00
coopops 724cd381cc [C28-16][@ant] feat: AbstractDeltaMapper.normalizeSignedDocuments + SignedDocField — Story 6.2
AbstractBlockchainDeltaMapper получает protected readonly signedDocumentFields
ReadonlyArray<SignedDocField> (default []) + helper normalizeSignedDocuments(data).
SignedDocField описывает путь к IChainDocument2-полю в TBlockchainData; bracket-
нотация поддерживает массивы: `appendix` (top-level), `statement.attachments[]
.signed_attachment` (nested-array, E12). parseSignedDocPath → PathSegment[],
applyAtPath in-place трансформирует через
DomainToBlockchainUtils.convertChainDocumentToDomainFormat.

appendix-delta.mapper.ts — эталон: ручной convertChainDocumentToDomainFormat
(value.appendix) заменён декларацией signedDocumentFields = [{ path: 'appendix' }]
+ this.normalizeSignedDocuments({ ...value }).

signed-document-normalization.test.ts (16) — парсер 4 кейса + normalize 7 кейсов
(top-level, nested-array, missing-field no-op, multiple fields, empty config,
null/undefined, immutability caveat).

delta-mapper-signed-doc.contract.test.ts (3) — guard: mapper с непустым
signedDocumentFields обязан вызвать this.normalizeSignedDocuments — иначе
silent data corruption (meta остаётся JSON-строкой, Story 6.4 checksum
не сходится).

IPFS lazy resolver (E14) и миграция остальных mapper'ов с ручной нормализацией —
вне scope, тречится Epic 9.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-06-02 07:21:09 +00:00
coopops 5aa1a21a97 [C28-16][@ant] feat: namespace db/bc/derived + replaceBc helper — Story 6.1
BaseDomainEntity получает generic <TDb, TBc>: this.db (shallow-copy databaseData),
this.bc (nullable, заполняется через utility replaceBc()), block_num/present/status
остаются на базе (hot-path stale-delta guard). Backward-compat: TBc=unknown по
дефолту — 22 legacy entity компилируются без изменений.

replaceBc вынесен utility-функцией, не методом класса — protected/public метод
ломает structural typing там, где Omit<XxxDomainEntity,...> используется в сигнатурах
репо (state-typeorm-repo).

ProjectDomainEntity — эталон: PROJECT_BC_KEYS как const satisfies, updateFromBlockchain
вызывает replaceBc(this, blockchainData, PROJECT_BC_KEYS) вместо запрещённого
Object.assign(this, blockchainData). Плоские поля остаются для legacy compat —
миграция остальных потребителей на entity.bc.* трекется Epic 9.5.

composite-entity.contract.test.ts — рекурсивно сканит src/**/*.entity.ts, для
не-legacy entity запрещает Object.assign(this, ...). Legacy allowlist на 22 файла
с явной отсылкой на Epic 9.5. 99/99 entity prove'нуты + Project явно проверен
на replaceBc + PROJECT_BC_KEYS.

controller/CLAUDE.md — секция Composite-Entity (ADR-008) актуализирована: BC_KEYS
с satisfies ReadonlyArray<keyof IXxxBlockchainData> — canonical-ordered источник
для Story 6.4 checksum.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-06-02 07:11:34 +00:00
coopops 933e5b5ffe [C28-14][@ant] feat: архив инвалидированных сущностей + retention LIB-1000 — Story 4.4
handleFork теперь не делает hard-delete, а атомарно переносит снесённые форком live-ряды
в invalidated_entities и инвалидированные снимки entity_versions в invalidated_entity_versions
(две таблицы — разные семантики). Порядок: archiveInvalidatedSince → restoreFromVersions →
archiveInvalidatedVersionsSince. forkEventId (controller-формат chain:fork:N:short) пробрасывается
от handleEvent → processFork → ForkRegistry.runAll → syncer.handleFork → архив.fork_event_id
для forensic-группировки.

BlockchainArchiveRetentionService (@Cron, default ежечасно) читает LIB через
BlockchainService.getInfo() и удаляет архив старше LIB-1000 блоков. RETENTION_HORIZON_BLOCKS=1000
хардкод (свойство сети, не оператора). Env-переключатели:
BLOCKCHAIN_ARCHIVE_RETENTION_ENABLED (default true), BLOCKCHAIN_ARCHIVE_RETENTION_CRON.

EntityVersioningService расширен archive-методами под DataSource.transaction. Контракт
IForkAwareSyncer.handleFork(forkBlockNum, forkEventId?) — обратно совместим (2-й optional).
IBlockchainSyncRepository.archive* — optional, fallback на старую find+delete для off-chain
(allowlist Story 4.3).

ScheduleModule.forRoot() добавлен в app.module (раньше не было).

Tests: 14 новых unit (entity-archive, retention, handleFork contract) + 52 регрессионных
(processFork, fork-registry, base-repo-contract, no-onevent) — 66 зелёных, tsc=0.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-28 16:43:10 +00:00
coopops d886d780fc [C28-14][@ant] test: contract guard BaseBlockchainRepository + block_num типизация — Story 4.3
Audit-проход без миграции рантайма. Полная карта entity/repo и сравнений
block_num — в blago _bmad-output/tracks/sync-arch/.../audit-report-4-3.md.

Изменения в коде:

1. tests/unit/blockchain/base-blockchain-repository.contract.test.ts — НОВЫЙ
   regression-guard. Сканирует все *.typeorm-entity.ts extends BaseTypeormEntity
   и для каждой ищет *.typeorm-repository.ts extends BaseBlockchainRepository.
   Allowlist OFF_CHAIN_BASE_ENTITIES для 5 off-chain артефактов (comment,
   cycle, issue, story, time-entry) — у них block_num унаследован vestigial,
   синкера нет, форк их не откатывает (корректно). Тест ловит регрессию,
   если кто-то добавит блокчейн-mirror entity без BaseBlockchainRepository
   — иначе entity_versions молча перестанут писаться, форк превратится в
   hard delete (silent data loss).

2. controller/CLAUDE.md — два новых правила:
   (a) разнобой типов block_num: BaseTypeormEntity (capital+shared) использует
       integer+number — корректно; ActionEntity/DeltaEntity/ForkEntity/
       SyncStateEntity — bigint+number type-mismatch (PG возвращает string,
       TS говорит number). Hot-path везде явно Number() либо PG bind, так
       что runtime safe. Технический долг в Epic 9 — bigint Transformer.
   (b) контракт «entity с block_num → repo extends BaseBlockchainRepository»
       + ссылка на regression test + allowlist OFF_CHAIN_BASE_ENTITIES.

3. tests/unit/blockchain/base-blockchain-repository.contract.test.ts:
   нюанс — entityKindFromFileName нормализует суффикс -typeorm (chairman
   approval-typeorm.entity.ts vs approval.typeorm-repository.ts mismatch
   имён файлов).

Findings (полное в audit-report-4-3.md):
- 25 entity extends BaseTypeormEntity; 20 имеют BaseBlockchainRepository.
- 5 без BaseBlockchainRepository — off-chain артефакты (легитимно).
- 4 infra entity с bigint+number type-mismatch (runtime safe, тех. долг).
- Direct typeormRepo.save для блокчейн-зеркал — НЕ найдено (контракт соблюдён).
- Все сравнения block_num в sync-core используют Number() или PG bind.

Tests: 2/2 contract-test зелёные.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-28 15:51:22 +00:00
coopops 68b37efbe9 [C28-14][@ant] refactor: снять DEC-013 pause-barrier и @OnEvent('fork::*') — Story 4.2
После Story 4.1 ForkRegistry уже даёт sequential rollback всех syncer'ов через
pull-DiscoveryService, а saveFork идёт прямым вызовом из processFork. Старый
broadcast-путь через EventEmitter ('fork::*' + emitAsyncWithTimeout с TTL
force-resume из Story 1.3 DEC-013) — рудимент: дублирует saveFork (через
BlockchainEventHandlerService.handleForkEvent), повторно зовёт handleFork в
каждом syncer'е (idempotent no-op после ForkRegistry, но лишний DB-traffic).

Удалено:
- @OnEvent('fork::*') + handle*Fork методы в 20 файлах:
  · 3 в infrastructure/database/typeorm/blockchain/services/ (user-agreement, user-wallet, agreement)
  · 16 в extensions/capital/application/syncers/
  · 1 в extensions/chairman/infrastructure/blockchain/services/ (approval)
  · 1 дубль saveFork в domain/parser/services/blockchain-event-handler.service.ts
  · orphan dead-метод в application/wallet/services/program-wallet-sync.service.ts
- Шаг 4 (deprecated emitAsyncWithTimeout) из BlockchainConsumerService.processFork.
- BLOCKCHAIN_FORK_PAUSE_TIMEOUT_MS из config/config.ts (zod + config объект).
- Упоминание env-var из controller/CLAUDE.md.

Что осталось:
- EventsService.emitAsyncWithTimeout — определение в infrastructure/events/events.service.ts.
  Каллеров в src/ нет; не удаляю утилиту — возможно пригодится для Epic 5
  (waitForDelta / pool retry). Удалят на следующем рефакторе если не использована.
- AbstractEntitySyncService.handleFork остаётся: его теперь зовёт только ForkRegistry.
- @OnEvent('action::*') и @OnEvent('delta::*') в BlockchainEventHandlerService —
  валидный dispatch pipeline (ADR-002), не трогаем.

Tests:
- processFork.test.ts: убраны expect'ы на emit; новый regression test что
  events.emit/emitAsyncWithTimeout НЕ вызываются с fork:: префиксом.
- НОВЫЙ tests/unit/blockchain/no-onevent-fork.test.ts: grep-guard по src/
  на @OnEvent('fork::*') (комментарии отфильтрованы) → fail на регрессии.
- Все 6 suites зелёные (52 теста), tsc --noEmit 0 errors.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-28 15:42:39 +00:00
coopops e810d3152f [C28-14][@ant] feat: ForkRegistry sequential apply форка — Story 4.1
Цель — снять параллельный @OnEvent('fork::*') broadcast в 20+ syncer-ов и
заменить на sequential обход через ForkRegistryService, что в сочетании
с single-active XREADGROUP parser2 даёт натуральный барьер форка (INV-T03,
NFR10). Старый broadcast путь оставлен deprecated на этот релиз — Story 4.2
удалит вместе с pause-barrier из DEC-013.

Реализация:
- shared/sync/fork/{interface,service,module}: IForkAwareSyncer + symbol-marker
  FORK_AWARE_MARKER, ForkRegistryService с pull-сбором через DiscoveryService
  на onApplicationBootstrap, sequential for-of await + priority-ordering.
- AbstractEntitySyncService: implements IForkAwareSyncer (marker через class
  field), handleFork теперь re-throw (catch удалён) — контракт sequential
  ForkRegistry.runAll. Не требует super.onModuleInit() у 20 наследников
  (DiscoveryService снимает push-зависимость).
- BlockchainConsumerService.handleEvent для fork: dedup-gate через
  computeForkEventId → processFork (runAll → deleteDedupAfterBlock → saveFork
  → deprecated emit) → markEventApplied. Для action/delta — markEventApplied
  теперь пишет block_num.
- ConsumerDedup: новая колонка block_num (bigint nullable) + индекс +
  deleteAfterBlock(blockNum). Старые NULL-записи не затрагиваются.
- event-id.util: новый computeForkEventId в формате chain:fork:block:short_id
  (полное «fork», единый стиль с action/delta — parser2-формат chain:f:... не
  используется).

Тесты (51 кейс, 5 suites):
- unit fork-registry: sequential apply, error propagation, priority, bootstrap
  discovery (15 кейсов).
- unit blockchain-consumer.processFork: порядок шагов, dedup-gate, mark после
  processFork, fail-paths, parser2-format isolation (11 кейсов).
- unit consumer-dedup repository: markApplied с/без blockNum, deleteAfterBlock
  edge-cases (8 кейсов).
- unit event-id.util: computeForkEventId детерминизм + поведение на коротком
  block_id (5 новых кейсов).
- integration fork-flow: bootstrap → delta(N+1)→fork(N)→delta(N+2), rollback
  не трогает <=N, error propagation (4 кейса с реальным Nest DI).

tsc 0 ошибок, jest 51/51 зелёные.

Spec: blago/production/13-platforma-tsifrovogo-kooperativa/components/14-versiya-3/_bmad-output/tracks/sync-arch/implementation-artifacts/spec-4-1-fork-kak-event-v-unified-stream.md

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-28 14:52:38 +00:00
coopops 99c22b0064 [C28-13][@ant] chore: обновить pnpm-lock.yaml до @coopenomics/parser2@1.1.0
Lockfile висел на 1.0.3, потому что 1.1.0 ещё не был опубликован
в npm в момент bump'а package.json. Сейчас 1.1.0 в реестре, pnpm
install подхватил его + новую транзитивную @coopenomics/coopos-ship-reader@0.2.0
и @napi-rs/nice@1.1.1.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-28 12:26:30 +00:00
ant 4c0fbefca9 Merge pull request 'Эпик 3 sync-arch: переезд транспорта controller с parser1 на parser2 ParserClient [C28-13]' (#35) from parser2-epic-3-transport into parser2
Reviewed-on: #35
2026-05-28 11:57:20 +00:00
coopops 8fdc99a7f9 [C28-13][@ant] feat: маппер parser2 отдаёт реальные поля action-трейса + dep parser2 1.1.0 — паритет с parser1, без заглушек
transaction_id/creator_action_ordinal/context_free/elapsed/console/
account_ram_deltas + receipt.auth_sequence теперь идут из ActionEvent
parser2 1.1.0 (добавлены в сам пакет + ship-reader 0.2.0). Нужны
ledger2 для cross-link родительского apply (transaction_id+action_ordinal)
и blockchain-explorer. tsc --noEmit контроллера против новых типов — чисто.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-25 17:08:24 +00:00
coopops 8d27c4e245 [C28-13][@ant] feat: заменить транспорт parser1 на parser2 ParserClient — единый движок без флагов
Контроллер читает события через @coopenomics/parser2 ParserClient вместо самодельного
consumer'а поверх Redis-стрима notifications (его писал parser1). Никаких флагов и
параллельной работы двух движков: одна система — либо работает на parser2, либо нет.

Удалена ручная обвязка (RedisStreamService, consumer-group, recoverOwnPending, XAUTOCLAIM,
XTRIM) — всё это ParserClient делает сам (single-active-lock, recover, dead-letter после
N провалов). Новый consume-loop ведёт генератор stream() вручную: next() при успехе
(XACK внутри parser2), throw() при ошибке (учёт провалов / dead-letter) — наивный for-await
неверен, проброс из тела не доходит до catch вокруг yield и убивал бы консьюмер.

Маппер parser2-event.mapper переводит ParserEvent → IDelta/IAction (DEC-T09), обработчики
processAction/processDelta/processFork не тронуты. Дедуп по event_id теперь безусловный
(флаг BLOCKCHAIN_DEDUP_ENABLED убран), формат event_id оставлен прежним (action/delta).

ВНИМАНИЕ: parser2 ActionEvent не несёт transaction_id/creator_action_ordinal — ledger2
cross-link родительского apply на них опирается; в маппере заглушки, проверить на прогоне.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-25 15:58:12 +00:00
coopops 0e3ccb4356 Revert "[C28-13][@ant] fix: выровнять формулу event_id под parser2 v1.0.3 — сверка перед cutover"
This reverts commit 306835d0fc.
2026-05-25 15:42:46 +00:00
coopops 306835d0fc [C28-13][@ant] fix: выровнять формулу event_id под parser2 v1.0.3 — сверка перед cutover
Локальная формула computeDeltaEventId/computeActionEventId расходилась с движком
parser2 (дискриминанты delta/action вместо a/d, block_id[0..8] вместо [0..16]).
Это закрывает сверку из Story 3.3 phase 2, перенесённую вперёд: computeEventId
теперь импортируем из опубликованного пакета. Выровнял байт-в-байт, golden-тест
сверен против исходника parser2 (delta и action совпадают). Без выравнивания при
overlap dual-consume один event получал бы два разных id в legacy и в движке и
dedup-gate промахнулся бы = silent data loss. Поправил формат event_id в CLAUDE.md.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-25 10:18:41 +00:00
ant 10e5b83ac9 Merge pull request 'Эпик 2 sync-arch: фундамент идемпотентности — event_id + consumer_dedup (релиз 1.1.1) [C28-12]' (#33) from parser2-epic-2-idempotency into parser2
Reviewed-on: #33
Reviewed-by: Алексей Муравьев <chairman.voskhod@gmail.com>
2026-05-25 10:05:56 +00:00
coopops 33d936e5c8 [C28-12][@ant] refactor: убрать DDL-миграцию consumer_dedup — таблицу создаёт synchronize:true через entity, отдельная миграция избыточна по текущей конвенции typeorm (ревью PR #33)
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-25 07:45:54 +00:00
coopops a73f07fa0c [C28-12][@ant] feat: локальное вычисление event_id с dual-write и dedup-gate за флагом — повтор события распознаётся как no-op, gate выключен до сверки формулы с parser2 в Epic 3 (Stories 2.2, 2.3, DEC-T08, DEC-020)
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-24 18:31:00 +00:00
coopops 77f358e865 [C28-12][@ant] feat: добавить таблицу consumer_dedup с миграцией и репозиторием — фундамент идемпотентности для распознавания повторно применённых событий блокчейна (Story 2.1, INV-09)
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-24 18:30:53 +00:00
ant 2afc71c281 Merge pull request 'Эпик 1 sync-arch: срочные фиксы синхронизации (релиз 1.1.1) [C28-11]' (#32) from parser2-epic-1-hardening into parser2
Reviewed-on: #32
2026-05-24 18:17:23 +00:00
coopops 9cf19aa8fe [C28-11][@ant] fix: барьер форка и вынос задержки action-emit в конфиг — откаты форка завершаются до обработки следующей дельты, исчезает хардкод 3000мс (Stories 1.3, 1.4, DEC-007)
Stories 1.3 + 1.4 затрагивают общие файлы (config.ts, blockchain-consumer.service.ts), поэтому одним коммитом:
- 1.4: ACTION_EMIT_DELAY_MS=3000 → config.blockchain.action_emit_delay_ms (env BLOCKCHAIN_ACTION_EMIT_DELAY_MS). Порядок save→ACK→setTimeout(emit) уже был корректен.
- 1.3: EventsService.emitAsyncWithTimeout + await в processFork = пауза consumer'а до завершения @OnEvent('fork::*')-откатов; TTL force-resume = config.blockchain.fork_pause_timeout_ms. Временно до Epic 3/ForkRegistry.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-24 17:38:42 +00:00
coopops 4b8121b0b7 [C28-11][@ant] fix: guard монотонности block_num в createIfNotExists — устаревшая дельта из раннего блока больше не затирает более свежую запись на create-пути (Story 1.1, DEC-008)
Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-24 17:38:41 +00:00
Alex Ant 970e107261 DEV setup on macos 2026-05-24 12:09:31 +05:00
claude a0e169e9b4 fix(blago-cli): pull не плодит ложные merge-конфликты при bump updated_at
Корневая причина: при pull конфликт объявлялся по условию
`dirty && remoteUpdatedAt !== prev.remote_updated_at`, где `dirty`
определяется сравнением raw-байтового sha файла с content_etag_local.
Серверные метки времени (updated_at/created_at) входят и во frontmatter
файла, и в etag. Когда сервер бьёт _updated_at родителя при дочерней
мутации (создание/удаление issue/story), etag в индексе расходится с
файлом ровно на строку updated_at — файл считается «грязным», а при
изменившемся remote_updated_at pull пишет маркеры слияния на весь файл,
хотя содержательно текст идентичен. Подтверждено: подстановка
remote_updated_at в файл воспроизводит etag байт-в-байт (58 записей на
проде voskhod).

Фикс: в syncEntityFile перед записью маркеров сравниваем локальный и
серверный тексты в каноне без updated_at/created_at. Если совпадают —
это не конфликт: принимаем серверную версию и лечим etag, без маркеров.
Реальная правка тела/заголовка по-прежнему даёт маркеры.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-24 12:00:43 +05:00
ant a93022343c Merge pull request 'test(ci): dry-run typecheck workflow on PR — duration measurement' (#30) from ci-trial-typecheck-2026-05-23 into dev
Reviewed-on: #30
2026-05-23 13:22:54 +00:00
claude 81fca02e39 Merge remote-tracking branch 'origin/dev' into ci-trial-typecheck-2026-05-23
Typecheck / desktop (pull_request) Successful in 13m8s
Typecheck / controller (pull_request) Successful in 12m54s
2026-05-23 16:10:24 +05:00
claude d1977e3da2 test(ci): retrigger after workflow fix (lerna run build)
Typecheck / desktop (pull_request) Successful in 12m22s
Typecheck / controller (pull_request) Failing after 6m31s
2026-05-23 15:49:12 +05:00
claude 69d0e223ed ci(typecheck): полный lerna run build вместо --scope cooptypes+factory(+sdk)
Trial run #148 (PR #30) упал в job controller на 37 TS2307 «Cannot find
module» для @coopenomics/{sdk,inter,notifications}. Локально маскируется
тем, что controller стартует через ts-node, который резолвит .ts напрямую
через tsconfig-paths/pnpm-симлинки и не зависит от dist/. tsc же ищет
types из package.json целевого пакета — а оно показывает на dist/index.d.ts
из unbuild.

Замена локального scoped-build на полный `pnpm lerna run build` (как в
корневом Dockerfile builder-стадии) собирает граф целиком и устойчиво
к добавлению новых workspace-пакетов. Добавляет ~2-3 мин ко времени job'а,
end-to-end оценочно ~21 мин (был 18 на сломанной версии).
2026-05-23 15:48:50 +05:00
claude b1b0776d68 test(ci): dry-run typecheck workflow on PR — measure end-to-end duration
Typecheck / desktop (pull_request) Successful in 12m35s
Typecheck / controller (pull_request) Failing after 6m31s
2026-05-23 10:57:59 +05:00
claude e4a1a33a53 ci: typecheck (vue-tsc desktop + tsc controller) — PR-гейт на dev и needs у release
build образов в release.yaml не ловит TS-ошибки: quasar build идёт через
esbuild с выключенным vueTsc в vite-plugin-checker (см. quasar.config.cjs),
а у controller'а build-скрипта вообще нет — `lerna run build` его молча
пропускает, в проде ts-node стартует и валится на типах только в рантайме.
Поэтому битый тэг мог уехать в DockerHub (кейс PR #392 / rename 1080→1020
в cooptypes — TS2551 в distribution-management проскочил именно так).

Новый reusable workflow .github/workflows/typecheck.yaml:
 - desktop: build cooptypes/factory/sdk → quasar prepare → vue-tsc --noEmit --skipLibCheck
 - controller: build cooptypes/factory → pnpm typecheck (tsc --noEmit)
 - триггер pull_request на dev + workflow_call

В release.yaml добавлен job typecheck (uses: ./.github/workflows/typecheck.yaml),
release-job получил needs: typecheck. Downstream publish-packages /
publish-docs / trigger-coopenomics-docs через release автоматически в цепочке.

Push в dev/testnet/main НЕ триггерит — PR-гейта достаточно, тэги покрыты
через workflow_call. Если vue-tsc упрётся в OOM/таймаут на ubuntu-latest,
fallback на `pnpm --filter @coopenomics/desktop run typecheck` (без SFC).
2026-05-23 10:48:53 +05:00
ant 9cbed2edf5 Merge pull request 'fix(controller): откатить transpileOnly — ломает TypeORM (post-PR#27 hotfix)' (#29) from fix/controller-revert-transpileonly into dev
Reviewed-on: #29
2026-05-23 05:29:52 +00:00
claude f27eb3a102 fix(controller): откатить "ts-node":{"transpileOnly":true} — ломает TypeORM
PR #27 включил transpileOnly через "ts-node" блок в tsconfig.json
для ускорения cold-start dev. Это сломало TypeORM на старте:

  DataTypeNotSupportedError: Data type "Object" in "TokenEntity.type"
  is not supported by "postgres" database.

Корень: transpileOnly режим ts-node использует ts.transpileModule,
один файл за раз без TypeChecker. Cross-file type aliases — типа
`import type { TokenType } from '~/types/token.types'` где
`TokenType = (typeof tokenTypes)[keyof typeof tokenTypes]` — без
type-checker'а **не резолвятся**. design:type metadata
для `@Column() type!: TokenType` записывается как `Object` вместо
`String`. TypeORM пытается создать колонку Object → unsupported.

Проблема структурная: множество TypeORM Entity в controller'е
используют `import type {SomeAlias}` + `@Column() field: SomeAlias`,
полагаясь на полный type-resolve в metadata-emit. Без явного `type:`
в каждом @Column переход на transpileOnly / SWC невозможен.

Возвращаемся к полному ts-node (cold-start 60+ сек, как было до
PR #27). @swc/core / @swc-node/register остаются в devDeps —
безвредны, не используются. Smoke-suite tests/unit/_swc-readiness/
остаётся как regression-net для будущих попыток (тестирует
emitDecoratorMetadata инвариант).

Будущий путь к ускорению (отдельная задача):
1. Пройтись по всем TypeORM Entity, добавить explicit type: в
   каждый @Column — снимет зависимость от cross-file metadata.
2. ИЛИ перевести TokenType-подобные type-aliases в enum (value-
   import) — runtime binding позволит metadata эмититься корректно.
3. Тогда transpileOnly / SWC заработают без regressions.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-23 10:27:49 +05:00
ant e3f4071b16 Merge pull request 'perf(controller): cold-start dev в ~25x (transpileOnly) + Node 22 + SWC-ready' (#27) from feat/controller-swc-builder into dev
Reviewed-on: #27
2026-05-23 05:19:33 +00:00
ant 3c87043d12 Merge pull request 'chore(infra): mongo standalone локально, без --replSet rs0' (#28) from chore/mongo-standalone-local into dev
Build bootstrap container / build (push) Successful in 2m25s
Reviewed-on: #28
Reviewed-by: Алексей Муравьев <chairman.voskhod@gmail.com>
2026-05-23 05:19:12 +00:00
claude 1a6f326aa4 chore(infra): mongo standalone локально, без --replSet rs0
Локально гоняем mongo как standalone. Раньше был --replSet rs0 +
rs.initiate в entrypoint, но проект не использует ни transactions
(нет startSession), ни change streams (нет .watch()), ни
readConcern:'majority' — replica-set серверно избыточен. Клиенты
(mongoose в controller, MongoClient в parser, notifications) уже
подключаются по URL без replicaSet=/directConnection= параметров,
для них переход прозрачен.

Бонусы:
- pnpm run reboot больше не висит на «MongoDB еще не готов
  (нет PRIMARY)»: на arm64 sleep 5 в entrypoint не успевал поднять
  mongod до того, как rs.initiate пытался выполниться, и rs.status()
  внутри try/catch ловил неправильную ошибку — replica config не
  применялся, oplog.rs не создавался, PRIMARY никогда не наступал
  (инцидент 2026-05-23).
- Старт mongo на 5-10 сек быстрее.
- Меньше состояния в volume — нет oplog/replica-config.

reboot.sh: ждать db.adminCommand({ping:1}) вместо db.hello().isWritablePrimary.

Прод-конфигурация (k8s/swarm) этого файла не использует — там
своя replica-схема для HA, не затронута.

Если в будущем потребуются transactions — вернуть --replSet rs0
+ rs.initiate в entrypoint обратно. Триггер: появление в коде
session = await mongoose.startSession() или .watch().

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-23 10:16:25 +05:00
ant 5fc2d90a85 Merge pull request 'ci: объединить релизные workflow и убрать Telegram-уведомления' (#26) from chore/ci-unify-release-workflows into dev
Build bootstrap container / build (push) Successful in 3m26s
Reviewed-on: #26
2026-05-23 04:55:20 +00:00
Alex Ant bc3a315790 ci: объединить релизные workflow в один, убрать Telegram-уведомления
Слияние в release.yaml через jobs+needs (последовательно):
- release (контракты+контейнеры+webhook, как раньше)
- publish-packages (если не -alpha) — был publish-packages.yaml
- publish-docs (не -alpha + main) — был publish-docs.yaml
- trigger-coopenomics-docs (не -alpha + main) — был build-contracts-docs.yaml

Удалено:
- build-contracts.yaml (ручной workflow_dispatch, сознательно вынесен из
  релиз-пути после инцидента 2026-05-13, пользователем подтверждено удаление)
- publish-packages.yaml, publish-docs.yaml, build-contracts-docs.yaml
  (содержимое перенесено в release.yaml как зависимые jobs)

Гейты унифицированы на !contains(github.ref, '-alpha') во всех publish-*
и trigger-* (раньше publish-docs/build-contracts-docs резали ещё
-beta/-rc/-test). IS_PROD в release-job остаётся на (alpha|beta|rc|test)
намеренно — webhook продакшна и тэг :latest должны быть строже.

Telegram-уведомления удалены из release.yaml и build-bootstrap.yaml.
Полагаемся на дефолтные email-уведомления Gitea-инстанса (mailer ENABLED=true).
Секреты TELEGRAM_BOT_TOKEN/TELEGRAM_CHAT_ID после merge можно удалить из репо.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-23 09:39:53 +05:00
Alex Ant 4a244c05e4 fix(controller): откат "ts-node":{"swc":true} → "transpileOnly":true
Полный SWC через ts-node наткнулся на TDZ-ловушку при загрузке
src/extensions/1ccoop/oneccoop-extension.module.ts:

  ReferenceError: Cannot access 'OneCoopPlugin' before initialization
    at Object.get OneCoopPlugin
    at oneccoop-secret-key.guard.ts:83 (line in transpiled SWC output)

Корень: circular import между oneccoop-extension.module.ts и
guard.ts (guard импортирует OneCoopPlugin для @Inject(forwardRef(...))
+ type annotation; module импортирует guard для providers). SWC
эмитит `Reflect.metadata("design:paramtypes", [OneCoopPlugin])`
при class-declaration `@Injectable()` — это runtime-обращение к
OneCoopPlugin до того, как oneccoop-extension.module.ts закончил
инициализацию. tsc/CommonJS-loader прощает (hoisted exports +
Object.defineProperty(get) для late-binding), SWC по строгой
ES-семантике — нет.

Масштаб системный, не локальный: 32 файла в src/ используют
forwardRef(() => Class), много из них в pattern @Inject + type
annotation в конструкторе. Под SWC каждый такой файл —
потенциальный TDZ. Чинить по одному (import type + lazy require
в forwardRef) — десятки правок с риском уронить тип-safety.

Решение: остаёмся на ts-node --transpileOnly. Тот же 25x cold-start
(~1 сек на пробе), tsc-семантика прощает циклы, никаких code-changes.
@swc/core и @swc-node/register оставляем в devDependencies —
готовы к будущему полному SWC, когда отдельной задачей разорвём
forwardRef-циклы (заменить class-on-class @Inject через string/Symbol
токены, либо вынести типы в отдельные файлы без cycle).

SWC-options через .swcrc как module.lazy:true проверены — не лечат,
проблема в decoratorMetadata, не в импортах.

Smoke-suite tests/unit/_swc-readiness/ — 4/4 PASS на transpileOnly,
emitDecoratorMetadata через barrel-import сохраняется.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-23 09:31:25 +05:00
Alex Ant 79e333db44 perf(controller): полный SWC через @swc-node/register + Node 22
Финал миграции: вместо ts-node --transpileOnly теперь полный SWC
(Rust-транспайлер) через ts-node "swc" mode. Установлены
@swc-node/register@^1.11.1 и @swc/core@^1.15.33 в controller.
tsconfig "ts-node" → { "swc": true, "files": true } (вместо
transpileOnly). Все 14 ts-node-вызовов очищены от --transpileOnly
(избыточно при swc).

Замер:
- ts-node + tsc (baseline): 26+ сек cold-start на простом скрипте
- ts-node --transpileOnly (Node 20): ~1.0 сек
- ts-node + swc (Node 22):           ~1.0 сек (та же скорость, но
  без потери типов — SWC всё ещё транспайлит, просто на Rust)

На полном controller-проекте dev-cold-start раньше был 60+ сек,
теперь — secunda-уровень (точно замерить можно только перезапустив
coopback в контейнере).

Node 22:
- nvm alias default 22 (Node 22.22.3 — требование Quasar 2.5.2,
  заодно убрал quasar-prepare warning при pnpm install).
- libxmljs2 native binary теперь совместим с runtime (на Node 20
  падал tests/unit/reports на NODE_MODULE_VERSION mismatch).

.npmrc в корне (`store-dir=./.pnpm-store`) — фиксирует store в
монорепе. Корень проблемы был: docker-coopback запущен от root и
писал в `/app/.pnpm-store` (= host's /home/ant/mono/.pnpm-store),
host-pnpm дефолтно искал в ~/.local/share/pnpm/store — отсюда
ERR_PNPM_UNEXPECTED_STORE. Relative-path в .npmrc устраняет
mismatch навсегда: и хост, и контейнер видят store через тот же
relative-путь от repo root.

Smoke-suite tests/unit/_swc-readiness/ — 4/4 PASS на SWC, что
формально подтверждает: emitDecoratorMetadata через barrel-import
сохраняется (Nest DI, class-validator, @ValidateNested + @Type все
получают правильные design:type/paramtypes из SWC).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-23 09:20:05 +05:00
Alex Ant 40be8fb60c test(cooptypes,controller): починить два протухших теста
cooptypes/test/wallets-registry.snapshot — `human_name` для
w.wal.wthdrw в src/ledger2/wallets.generated.ts получил суффикс
"(deprecated, не используется в новых операциях)" (видимо, при
свежей регенерации из C++), но snapshot не обновили. Updating.

controller/tests/unit/process-registry — apply-anchor data поле
переименовано action_code → operation_code в самом сервисе
(src/domain/process-registry/services/process-registry.service.ts),
вместе с константой ACTION_CODE_TO_PROCESS_TYPE → OPERATION_CODE_TO_PROCESS_TYPE.
В тесте оставались старые имена → 1 из 6 кейсов падал на mismatch
regex'а сообщения ошибки. Переименовываю action_code → operation_code
во всём файле и обновляю regex (f2).

Что НЕ починено в этом коммите (pre-existing, не моё):
- 5 case'ов (a..e) в том же файле всё ещё падают: они используют
  operation_codes 'sov.axncnv' / 'cap.act2shr' / 'cap.act2ln' /
  'wall.depcpl' / 'reg.entrfee' / 'reg.minshare' / 'mig.opncash',
  которых нет в Ledger2.LEDGER2_OPERATION_REGISTRY (cooptypes).
  Test fixtures устарели относительно текущей канонической
  ledger2-онтологии (canonical имена — o.cap.crtnma, o.cap.dbtwrf,
  o.cap.lend, o.cap.repay, o.reg.payent, o.reg.putmin и т.п.).
  Этот тест-suite надо переписать под актуальный operation registry
  отдельным PR (требует знания canonical naming kanon).
  Падает и на dev (без моих правок) — это pre-existing tech debt.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-23 01:47:33 +05:00
Alex Ant 9e022443ca perf(controller): ts-node --transpileOnly во всех dev-скриптах
Cold-start controller dev (`pnpm dev`) сейчас 60+ секунд из-за полной
TypeScript-компиляции в ts-node на каждый рестарт nodemon. Решение —
добавить --transpileOnly во все 14 ts-node-скриптов и зафиксировать
это в tsconfig "ts-node" блоке. Транспайл-онли пропускает type-check,
оставляет только TS→JS transform (с сохранением emitDecoratorMetadata).

Замер на standalone-пробе с barrel-импортом + Reflect.getMetadata
(tests/unit/_swc-readiness/transpile-only-probe.ts):
- baseline (полный ts-node): 26+ сек (показал тест ts-jest)
- ts-node --transpileOnly:    ~1 сек

Ускорение ~25x на cold-start. dev / start / migration:* / init:* /
analyze:modules / generate-schema — все на --transpileOnly.

Типы продолжаем проверять отдельно: `pnpm typecheck` (tsc --noEmit
по этому же tsconfig.json) — это и так стоит делать перед коммитом
по правилам проекта.

Safety-net — smoke-suite tests/unit/_swc-readiness/swc-readiness.test.ts:
ловит главный риск SWC/transpile-only регрессий — потерю metadata на
barrel-импортах (поведение тех же кодпутей, что и в реальных Nest-
сервисах с injection через @Inject и class-validator DTO).
- ServiceB DI через barrel: design:paramtypes = [ServiceA] (не Object)
- @ValidateNested + @Type через barrel: nested design:type = NestedPayload
- Nest Test.createTestingModule резолвит сервисы через barrel-import
- class-validator/class-transformer не теряют type info

Если позже понадобится **полный SWC** (Rust-транспайлер, ещё в разы
быстрее) — добавить @swc/core + @swc-node/register в devDependencies
и переключить ts-node на swc-режим:
1. `pnpm add -D @swc/core @swc-node/register -F @coopenomics/controller`
2. В tsconfig.json "ts-node" → добавить `"swc": true` либо
   использовать `node --import @swc-node/register/esm-register` в скриптах.
Этот шаг не делается сейчас, так как install требует sudo на shared
pnpm-store (root-owned /home/ant/mono/.pnpm-store/v10) — пользователь
утром может сделать руками.

tsc --noEmit зелёный за 32 сек, smoke-suite + 1 case onboarding-ttl + 1 case
onboarding-steps-registry — все зелёные на baseline и после изменения
tsconfig.json.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-23 01:36:36 +05:00
Alex Ant 5fd5db0604 perf(desktop): отключить vueTsc в vite-plugin-checker dev
В dev-режиме vue-tsc через vite-plugin-checker удерживал постоянную
100% загрузку CPU и 2–4 GB RAM на больших Vue 3 + Quasar проектах
(Milkdown / BPMN-js / VueFlow / Mermaid / OpenLayers). Каждое
сохранение запускало полный re-typecheck в фоне, что в долгих
сессиях выглядело как утечка памяти и вешало машину.

Типы продолжаем гонять отдельно: `pnpm typecheck` (tsc --noEmit
--skipLibCheck) и через Volar в IDE. eslint в checker'е остаётся —
он лёгкий и полезен для overlay'я.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-23 01:20:25 +05:00
Alex Ant adc5926fa7 Merge branch 'main' into dev
Build bootstrap container / build (push) Failing after 4m59s
2026-05-23 00:55:56 +05:00
Alex Ant 655a73e828 chore(release): publish
Build bootstrap container / build (push) Failing after 7m45s
Trigger Contracts Docs Deploy / gate (push) Successful in 2m3s
Publish Docs / gate (push) Successful in 2m4s
Publish Packages / build-and-publish (push) Failing after 9m24s
Release / release (push) Failing after 4m33s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 3s
Publish Docs / build-and-publish-docs (push) Failing after 1h29m50s
2026-05-23 00:55:52 +05:00
Alex Ant 02418af616 Merge branch 'main' into dev
Build bootstrap container / build (push) Failing after 4m58s
# Conflicts:
#	components/blago-cli/package.json
#	components/boot/package.json
#	components/cleos/package.json
#	components/contracts/package.json
#	components/controller/package-lock.json
#	components/controller/package.json
#	components/cooptypes/package.json
#	components/desktop/package.json
#	components/docs-harness/package-lock.json
#	components/docs-harness/package.json
#	components/docs/package.json
#	components/factory/package.json
#	components/inter/package.json
#	components/migrator/package.json
#	components/notifications/package.json
#	components/parser/package-lock.json
#	components/parser/package.json
#	components/sdk/package.json
#	components/setup/package.json
#	lerna.json
2026-05-23 00:54:46 +05:00
Alex Ant 3d4f75bff0 chore(release): publish
Build bootstrap container / build (push) Failing after 7m29s
Trigger Contracts Docs Deploy / gate (push) Successful in 2m4s
Publish Docs / gate (push) Successful in 2m4s
Publish Packages / build-and-publish (push) Failing after 6m39s
Release / release (push) Failing after 4m27s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 2s
Publish Docs / build-and-publish-docs (push) Failing after 8m22s
2026-05-23 00:52:06 +05:00
Alex Ant 7b9828ae87 chore(release): publish
Build bootstrap container / build (push) Failing after 7m34s
Trigger Contracts Docs Deploy / gate (push) Successful in 2m17s
Publish Docs / gate (push) Successful in 2m5s
Publish Packages / build-and-publish (push) Failing after 9m49s
Release / release (push) Failing after 4m29s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 5s
Publish Docs / build-and-publish-docs (push) Failing after 8m30s
2026-05-23 00:50:01 +05:00
Alex Ant fb7ea468fa chore(release): publish
Build bootstrap container / build (push) Failing after 2m50s
2026-05-23 00:39:08 +05:00
Alex Ant 745438ded3 chore(release): publish 2026-05-23 00:39:08 +05:00
Alex Ant 82d58c29f6 chore(release): publish 2026-05-23 00:39:08 +05:00
Alex Ant aa5c180be0 chore(release): publish 2026-05-23 00:39:08 +05:00
Alex Ant e745c73cb5 chore(release): publish 2026-05-23 00:39:08 +05:00
Alex Ant f531182541 chore(release): publish 2026-05-23 00:39:08 +05:00
Alex Ant 2eadc79ee3 chore(release): publish 2026-05-23 00:39:08 +05:00
Alex Ant 52d423ef8a chore(release): publish 2026-05-23 00:39:08 +05:00
Alex Ant 2b529d5a15 chore(release): publish
Trigger Contracts Docs Deploy / gate (push) Successful in 2m12s
Build bootstrap container / build (push) Failing after 7m29s
Publish Docs / gate (push) Successful in 2m29s
Publish Packages / build-and-publish (push) Has been skipped
Release / release (push) Failing after 4m45s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Has been skipped
Publish Docs / build-and-publish-docs (push) Has been skipped
2026-05-23 00:38:30 +05:00
Alex Ant 5a17bcdfaf Merge branch 'dev' into testnet 2026-05-23 00:38:14 +05:00
Alex Ant fd59678944 local update
Build bootstrap container / build (push) Failing after 6m54s
2026-05-23 00:37:36 +05:00
Alex Ant 23605d2b81 chore(release): publish
Build bootstrap container / build (push) Failing after 7m29s
Trigger Contracts Docs Deploy / gate (push) Successful in 2m5s
Publish Docs / gate (push) Successful in 2m6s
Publish Packages / build-and-publish (push) Has been skipped
Release / release (push) Failing after 4m51s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Has been skipped
Publish Docs / build-and-publish-docs (push) Has been skipped
2026-05-22 17:34:24 +05:00
Alex Ant efce39a4c9 Merge branch 'dev' of ssh://git.coopenomics.world:222/C9S/mono into dev 2026-05-22 17:29:29 +05:00
coopops ba335432a2 docs(CLAUDE.md): разрешить прямые коммиты в dev mono-ai-1 для мелких фиксов 2026-05-22 12:29:01 +00:00
coopops 1b9cb27030 fix(controller): AWAITING_AUTHORIZATION в statusLabels PaymentDomainEntity
getStatusLabel() требует Record<PaymentStatusEnum, string>, AWAITING_AUTHORIZATION
был добавлен в enum, но забыт в локальном маппинге → ts-node краш в dev.
2026-05-22 12:28:58 +00:00
Alex Ant e000ff9c8f Merge branch 'dev' of ssh://git.coopenomics.world:222/C9S/mono into dev 2026-05-22 16:44:06 +05:00
coopops fdd09d5501 fix(boot): не тянуть vitest в production-цепочке init/
Build bootstrap container / build (push) Failing after 7m23s
`init/cooperative.ts` и `init/participant.ts` импортировали
`signProgramAgreement` из `tests/wallet/`, который на верхнем уровне делал
`import { expect } from 'vitest'`. При запуске `esno src/index.ts boot`
vitest падал с «Vitest failed to access its internal state», потому что
исполнялся вне vitest-воркера.

- Перенёс реализацию в `init/sign-program-agreement.ts`,
  `expect(...).toBeDefined()` заменил на обычные `throw new Error(...)`.
- `getCoopProgramWallet` инлайнил (через `walletUtils` тащился второй
  module-level `import expect from 'vitest'`).
- `tests/wallet/signProgramAgreement.ts` теперь реэкспортирует из init/,
  чтобы существующие тесты продолжали работать.
- Заодно убрал дохлый `import { describe, expect, it } from 'vitest'` из
  `init/participant.ts` (символы в файле не использовались) + неиспользуемые
  axios/Registry/sendPost.../sleep/GOVERN_SYMBOL/SYMBOL.
2026-05-22 11:43:19 +00:00
Alex Ant 0504c46fbd chore(release): publish
Build bootstrap container / build (push) Failing after 4m15s
Trigger Contracts Docs Deploy / gate (push) Successful in 2m4s
Publish Docs / gate (push) Successful in 2m3s
Publish Packages / build-and-publish (push) Failing after 8m4s
Release / release (push) Failing after 4m31s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 2s
Publish Docs / build-and-publish-docs (push) Failing after 8m16s
2026-05-22 14:44:59 +05:00
Alex Ant 6270ae14bf chore(release): publish
Build bootstrap container / build (push) Failing after 2m27s
Trigger Contracts Docs Deploy / gate (push) Successful in 2m15s
Publish Packages / build-and-publish (push) Has been skipped
Publish Docs / gate (push) Successful in 7m15s
Release / release (push) Failing after 9m33s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Has been skipped
Publish Docs / build-and-publish-docs (push) Has been skipped
2026-05-22 14:43:43 +05:00
Alex Ant 2a296ef2ef Merge branch 'dev' of ssh://git.coopenomics.world:222/C9S/mono into dev 2026-05-22 14:42:19 +05:00
ant a8f2b31494 Merge pull request 'fix(boot): test-helper'ы подписания программных соглашений — wallet::signagree вместо soviet::sndagreement' (#19) from fix/boot-tests-wallet-signagree-v2 into dev
Build bootstrap container / build (push) Failing after 2m25s
Reviewed-on: #19
Reviewed-by: Алексей Муравьев <chairman.voskhod@gmail.com>
2026-05-22 07:07:29 +00:00
ant 52a5871330 Merge pull request 'fix(ledger2,wallet): BURN_BLOCKED для возврата паевого + удаление approvewthd' (#20) from feat/ledger2-burn-blocked-withdraw into dev
Reviewed-on: #20
Reviewed-by: Алексей Муравьев <chairman.voskhod@gmail.com>
2026-05-22 07:06:39 +00:00
ant 1f10a3c092 Merge pull request 'fix(gateway): исходящий платёж скрыт от кассира до решения совета' (#21) from fix/wallet-withdraw-gateway-timing into dev
Reviewed-on: #21
Reviewed-by: Алексей Муравьев <chairman.voskhod@gmail.com>
2026-05-22 07:03:52 +00:00
ant 9579ae0612 Merge pull request 'fix(mono-base): install ca-certificates in runtime stage' (#22) from fix/mono-base-ca-certificates into dev
Reviewed-on: #22
2026-05-22 07:02:58 +00:00
ant a436527248 Merge pull request 'feat(chatcoop): транскрипция — снять лимит memo 4000, скилл blago transcription memo' (#23) from feat/chatcoop-transcription-memo into dev
Reviewed-on: #23
Reviewed-by: Алексей Муравьев <chairman.voskhod@gmail.com>
2026-05-22 06:59:29 +00:00
coopops 94e44df124 fix(chatcoop): TranscriptionMemoEditor — карточка с рамкой, заголовок секции, кнопка снизу
- WrappedEditor (q-field+Editor) на странице транскрипции выглядел сломанным: floating-label «Заметка о звонке» падал поверх первой строки memo, кнопка «Сохранить» торчала сбоку без выравнивания, рамки редактора не было.
- Перешёл на голый Editor (Milkdown через src/shared/ui/Editor) в собственной карточке: border-radius:10px, рамка по тону --tr-border, padded=true. Кнопка «Сохранить» — в нижней панели карточки (border-top, flex-end). Hint «доступно председателю и членам совета» — отдельной строкой под карточкой.
- TranscriptionDetailPage: добавлен h2 «Заметка о звонке» как у секции «Текст», memo больше не висит без подписи.
2026-05-22 06:33:37 +00:00
coopops dfed3774b7 feat(chatcoop): TranscriptionsPage — полноширинная q-table как в CalendarPage
Список транскрипций был зажат max-width: 720px в центре страницы и собран из самописных rows. Заменил на тот же паттерн, что использует CalendarPage / CalendarEventsTable — q-page(padding) + q-table с колонками: Звонок (название + превью memo), Начало, Длительность, Участники, Статус. Клик по строке открывает детальную страницу транскрипции.
2026-05-22 06:25:23 +00:00
coopops 3950aa75db feat(chatcoop): memo через WrappedEditor + расширить TranscriptionDetailPage до 1040px
- TranscriptionMemoEditor: q-input type=textarea заменён на WrappedEditor (Milkdown через src/shared/ui/WrappedEditor) — теперь memo отображается с markdown-рендерингом (заголовки/списки/жирный/ссылки), а не как plain текст. Кнопка «Сохранить» вынесена в отдельную панель под редактором (фокус-кольцо и поле растут естественно). Минимальная высота 180px, без скролла — растёт по содержимому.
- TranscriptionDetailPage: max-width 720 → 1040px, padding 16/20 → 16/32 — страница перестала быть сильно зауженной, гармонично для desktop.
- скилл manage-transcription-memo: добавлен раздел «Формат содержимого .memo.md» — первая строка строго одно предложение ≤150 символов без markdown (о чём был звонок), затем пустая строка и сжатая суть; этикет/повторы/разогрев убираются.
2026-05-22 06:05:56 +00:00
coopops db25c1dfa9 fix(blago-cli): blago pull бэкфилит .memo.md для всех COMPLETED транскрипций (не только новых)
Курсор transcriptionLastEndedExclusiveByProject фильтровал ВСЕ артефакты транскрипции — поэтому
для уже скачанных meeting.md sibling-файлы .memo.md не появлялись. Разделил циклы:

  1. meeting.md — только endedAt > lowerBoundExclusive (тяжёлый GetTranscription с сегментами).
  2. .memo.md  — для всех COMPLETED транскрипций каждый pull (поле memo приходит уже в лёгком
     GetTranscriptions, повторных запросов не делаем).

Проверено: blago pull → 4/4 sibling .memo.md появились пустыми в проекте 33-platforma-otchetov-dlya-fnsfss; затем blago transcription memo опубликовал 476 символов в крайней транскрипции 7116fb31-3b8c-4a63-9c0c-11da26aba075, повторный pull сохранил содержимое без конфликта.
2026-05-22 06:00:58 +00:00
coopops e38762deaa feat(blago-cli): blago pull всегда создаёт sibling .memo.md, baseline/merge без warnings
- pull-communication: для каждой COMPLETED-транскрипции вызывает syncTranscriptionMemoFile, который ВСЕГДА обеспечивает файл meetings/<stem>.memo.md (пустой, если на сервере memo пуст). Файл сразу индексируется (entity_type=call_transcription_memo) — редактирование→blago transcription memo идёт без шагов «создать файл».
- Конфликты при отсутствии prev-индекса разруливаются явно: server пуст → принять локальный draft как baseline; оба непустые и разные → git-style merge-markers; совпало → проиндексировать как есть.
- update-transcription-memo: текст ошибки про отсутствующий sibling указывает на blago pull (создаст sibling сам).
- скилл manage-transcription-memo: процедура переписана под «sibling уже есть, просто открой и редактируй».
2026-05-22 05:52:53 +00:00
coopops d2c1d425fc feat(blago-cli): blago pull тянет memo транскрипций в meetings/<stem>.memo.md
- новый entity_type call_transcription_memo в index-store (тип файла .memo.md, parsing/sync через стандартный syncEntityFile)
- pull-communication: для каждой COMPLETED-транскрипции с непустым tr.memo пишет sibling-файл meetings/<stem>.memo.md (hash = "<uuid>:memo"); при наличии локального draft, не индексированного в .blago/index.json, серверный memo не записывается — выводится warning
- update-transcription-memo: после успешной мутации сохраняет sibling и заносит запись в индекс (etag локального файла), чтобы следующий pull шёл штатно через syncEntityFile вместо warning'а
- скилл manage-transcription-memo: добавлены замечания про pull-синк, git-style маркеры конфликта и поведение неиндексированных черновиков
2026-05-22 05:44:46 +00:00
coopops ef993baa25 feat(blago-cli): команда transcription memo + скилл manage-transcription-memo
- `blago transcription memo <pathOrId> [--file <path>] [--text <inline>]` — публикация краткого содержания транскрипции через chatcoopUpdateTranscriptionMemo
- pathOrId: путь к meetings/<stem>.md (id из .blago/index.json, entity_type=call_transcription) или UUID
- default-источник memo — sibling-файл meetings/<stem>.memo.md рядом с meeting (pull-only, в push не уходит)
- скилл ai/commands/manage-transcription-memo.md описывает workflow «прочитать meeting → собрать .memo.md → согласовать → опубликовать»
2026-05-22 05:40:30 +00:00
coopops adf36b28cb feat(chatcoop): убрать лимит 4000 на memo транскрипции, оставить редактирование только chairman/member
- backend: убран @MaxLength(4000) с UpdateCallTranscriptionMemoInputDTO.memo и описание лимита из @Field
- backend: chatcoopUpdateTranscriptionMemo больше не доступен роли user, только chairman/member (read-методы — без изменений)
- desktop: TranscriptionMemoEditor больше не задаёт maxlength и counter в q-input
2026-05-22 05:40:20 +00:00
coopops 223dd00f91 fix(mono-base): install ca-certificates in runtime stage
@livekit/rtc-node (Rust + rustls + rustls-native-certs) reads root CAs
only from the system trust store. node:22-slim ships without
ca-certificates, so without /etc/ssl/certs/ca-certificates.crt every TLS
handshake from native bindings fails with
"invalid peer certificate: UnknownIssuer" — even for a valid LE chain.
Node.js itself is unaffected (own embedded CA bundle).

Incident 2026-05-21: secretary in dicoop/coopback:v2026.5.21-2 could not
connect to wss://chatcooprtc.coopenomics.world (controller logs full of
SecretaryAgentService UnknownIssuer; nginx on api-prod never saw the
handshake — broken before HTTP upgrade). Hot-fix on
voskhod-coopback-blue (docker cp ca-certificates.crt + restart)
restored secretary connectivity; this commit makes the fix permanent
in the base image so every consumer of dicoop/mono-base
(coopback / desktop / cooparser / notifications / boot) inherits it
on the next release tag.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-21 13:21:26 +00:00
coopops fd2f716e61 fix(gateway): исходящий платёж скрыт от кассира до решения совета
Pre-mature payment row: при wallet.interactor.ts::createWithdraw платёж
сразу появлялся в gateway PG со status=PENDING — кассир видел заявку
как готовую к выплате ДО того как совет её утвердил.

Минимальный фикс без переписывания create/sync-цепочки:

- PaymentStatusEnum += AWAITING_AUTHORIZATION (с лейблом «Ожидает
  решения совета»). Initial status в gateway.interactor.createWithdraw
  переключён с PENDING на AWAITING_AUTHORIZATION.
- Новый WithdrawAuthorizationListener в gateway.module:
  - on-chain `wallet::authwthd` (совет авторизовал)
    → AWAITING_AUTHORIZATION → PENDING (кассир увидит и сможет подтвердить).
  - on-chain `wallet::declinewthd` (совет/Gateway отказал)
    → AWAITING_AUTHORIZATION → CANCELLED.

UI кассира (desktop) должен в отдельном PR фильтровать AWAITING_AUTHORIZATION
из списка платежей (текущие компоненты, скорее всего, и так не показывают
неизвестный статус). PAYMENT_STATUS_LABELS подхватится автоматически.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-21 10:34:50 +00:00
coopops 33a414c7e7 fix(ledger2,wallet): возврат паевого взноса — BURN_BLOCKED из заблокированной суммы
Завершение возврата паевого (o.wal.wthcpl) переключено с TRANSFER
(SHARE_FUND_PAY → WITHDRAWALS_SINK) на новый WalletOp::BURN_BLOCKED:
заблокированная при createwthd сумма сжигается на кошельке пайщика,
получателя на цепи нет — деньги уходят из системы банковским переводом.

Чинит assertion 'walletop TRANSFER: недостаточно L3-средств' на
completewthd: после REQUEST_WITHDRAW (BLOCK) сумма лежит в L3.blocked,
а TRANSFER проверял L3.available.

Изменения:
- ledger2: WalletOp::BURN_BLOCKED=6 + case в walletop.cpp (списание из
  L2/L3 blocked). OPERATION_REGISTRY: o.wal.wthcpl с BURN_BLOCKED, без
  wallet_to. burn_pattern_correct обобщён на оба BURN-варианта.
- cooptypes: WalletOp += 'BURN_BLOCKED'; o.wal.wthcpl wallet_to=null.
- wallets.hpp: WITHDRAWALS_SINK (w.wal.wthdrw) помечен DEPRECATED —
  остаётся в реестре для исторических L2-балансов.
- standard p.wal.wthdrw: приведён к коду — одностадийный flow
  (pending → authorized → completed), без approvewthd.
- wallet::approvewthd удалён как dead code: action не в whitelist
  callback'ов, из createwthd создаётся повестка сразу с callback=authwthd.
  Удалены: .cpp, declaration в wallet.hpp, include в wallet.cpp, struct
  и action в abi_json/wallet.json.
- sov.authpkg.standard.yaml: упоминание approvewthd → authwthd.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-21 10:24:44 +00:00
coopops d128f245b7 fix(boot): test-helper'ы подписания программных соглашений — wallet::signagree вместо soviet::sndagreement
После Эпика 2 / компонента 48 `soviet::sndagreement` отказывается на
`program_id > 0`, программные соглашения переехали в контракт wallet
(`wallet::signagree`, ADR-008). Соответственно boot test helper'ы
(`signWalletAgreement`/`signCapitalAgreement`/`signGenerationContract`)
и две точки `init/*` (`participant.addUser`, `cooperative.createCooperative`),
которые ещё дёргали `soviet::sndagreement` через `signAgreement`/
`blockchain.sendAgreement` с `agreement_type ∈ {wallet, blagorost, generator}`,
падали в beforeAll тестов на ассерте контракта.

Делаем:
- Новый общий helper `tests/wallet/signProgramAgreement.ts` —
  обёртка над `wallet::signagree` с auth=coopname@active. Проверяет, что
  в `wallet::users[username].programs[]` появилась запись с нужным
  `program_id`. Возвращает `{wallet, program, txId}` — той же формы,
  что прежние helper'ы (downstream-тесты остаются без изменений).
- Три исторических helper'а становятся тонкими обёртками над ним:
  `signWalletAgreement` → (program_id=1, draft_id=1),
  `signCapitalAgreement` → (program_id=4, draft_id=1000),
  `signGenerationContract` → (program_id=3, draft_id=0).
- `tests/capital/consts.ts` — добавлены `walletDraftId`/`sourceDraftId`/
  `capitalDraftId`, соответствующие мапе `program_map` в
  `lib/core/programs.hpp` (источник правды).
- `init/participant.ts` (`addUser`) и `init/cooperative.ts`
  (`createCooperative`) — `blockchain.sendAgreement(...agreement_type='wallet')`
  заменён на `signProgramAgreement(...program_id=1, draft_id=1)`.

`tests/soviet/signAgreement.ts` оставлен как есть — он по-прежнему нужен
для не-программных типов соглашений (`signature`/`user`/`privacy`,
program_id=0), которые остались за `soviet::sndagreement`.

Не входит:
- Замена `getUserProgramWallet` (читает legacy `soviet::progwallets`)
  на чтение `wallet::users` в downstream-тестах — отдельный технический
  долг, не блокирует beforeAll.
2026-05-21 08:16:27 +00:00
Alex Ant 1c7a3afc81 chore(release): publish
Publish Docs / gate (push) Successful in 2m4s
Trigger Contracts Docs Deploy / gate (push) Successful in 2m5s
Publish Packages / build-and-publish (push) Failing after 8m48s
Release / release (push) Failing after 7m22s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 6s
Publish Docs / build-and-publish-docs (push) Failing after 8m57s
2026-05-21 13:05:02 +05:00
Alex Ant c0627b53e3 chore(release): publish
Trigger Contracts Docs Deploy / gate (push) Successful in 2m6s
Publish Docs / gate (push) Successful in 2m9s
Publish Packages / build-and-publish (push) Has been skipped
Release / release (push) Failing after 4m28s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Has been skipped
Publish Docs / build-and-publish-docs (push) Has been skipped
2026-05-21 13:01:24 +05:00
Alex Ant ea8695d1fc Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-21 13:00:41 +05:00
ant bf3f9ca5ac Merge pull request 'fix(capital): w.cap.gen → COOPERATIVE — снять L3-проверку, чинит convertsegm при CRPS' (#18) from feat/capital-w-cap-gen-cooperative into dev
Reviewed-on: #18
2026-05-21 07:47:51 +00:00
coopops f023d3a8c8 fix(capital): w.cap.gen на COOPERATIVE — снять L3-проверку, чинит convertsegm при CRPS-перераспределении
На voskhod walletop `convertsegm` падал «недостаточно L3-средств у
пайщика» в проектах, где CRPS-перераспределение увеличивало долю
contributor'а. Причина: `w.cap.gen` был USER_SHARED, а CRPS в
`approvecmmt` не делал per-user компенсирующих TRANSFER между сегментами:
инвариант `Σ COMMIT_RID == Σ ACCEPT_RID` соблюдался только на проекте,
не на сегменте, и L3-проверка walletop ломала convertsegm у пайщиков,
чья доля выросла через CRPS.

Фикс — переключение `w.cap.gen` с USER_SHARED на COOPERATIVE (ADR-002):
генератор становится единым кооперативным пулом без L3, walletop
проверяет только L2-баланс пула. `convertsegm` любого пайщика берёт из
общего котла ровно `segment.available_for_program` без проверки
персонального остатка.

Изменения:
- wallets.hpp: GENERATOR_FUND kind USER_SHARED → COOPERATIVE.
- signact2.cpp: коммент-инвариант — закрытие 08 на программе, не на
  сегменте (L3-разрез по пайщику снят).
- ledger2::migrate(): переписан на cleanup осиротевших userwallets
  [voskhod, w.cap.gen, *] прямым erase. Старая legacy → ledger2
  миграция убрана (meta.migrated=true в проде), сигнатура сжата до
  пустых скобок. migrate теперь — универсальная точка расширения
  для разовых исправлений состояния ledger2, по аналогии с
  capital::migrate.

migrate3 и capital::migrate сознательно не трогаются: migrate3 —
низкоуровневая per-record миграция L3 со своим назначением (не для
очистки чужой таблицы); capital::migrate остаётся пустой точкой
расширения капитала.

L2 `wallets2[w.cap.gen]` = Σ старых userwallets — синхронен на момент
перехода (проверено по фактическим данным voskhod).

Не входит в этот PR: балансовая корректировка для уже застрявших
пайщиков на voskhod — отдельной миграцией-скриптом после деплоя.

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-21 07:45:50 +00:00
Alex Ant 5de2d2bba1 feat(boot:extra): засев partner1 как coop-пайщика в воскход для E2E Эпика 0 (#410)
Build bootstrap container / build (push) Failing after 3m12s
* fix(controller): IS_UNIONED zod-парсер принимает string из .env

z.boolean().default(true) валится для переменной из .env, потому что
process.env всегда отдаёт строку: zod не приводит "true"/"false" к
boolean, в результате validateEnv падает с «IS_UNIONED: параметр не
установлен» и coopback не стартует, если в .env стоит IS_UNIONED=false
(стандартный dev-обход messenger-гейта, см. flow подключения партнёра).

Заменено на string().default('true').transform(v => v === 'true') —
сохранение прежнего default=true и поддержка string-форм из env.

* feat(epic-0): partner onboarding harness — signin → sign agreements → connect

Что добавлено:
- desktop/quasar.config.cjs: vite server.allowedHosts для voskhod-dev/
  partner-dev/api-dev (Vite 5.4+ блокирует cross-origin Host без явного
  списка — иначе SSR/HMR-сервер возвращает 403 «Blocked request»).
- docs-harness/lib/harness.mjs: helper signOnboardingAgreements —
  реальная подпись каскада SignAgreementDialog (wallet/signature/
  privacy/user), каждый клик отправляет sendAgreement → wallet::signagree
  on-chain. В отличие от dismissOnboardingDialogs делает on-chain эффект
  (см. inc 2026-05-18: stale vault SERVER_SECRET → bad decrypt).
- scenarios/onboarding/01..07: новый partner-flow Эпика 0 — partner1
  заходит в Восход, подписывает 4 типовых соглашения, идёт на «Подключение»,
  ant одобряет, наблюдаем установку partner-dev.
- scenarios/registration/01..04: архив старого registration-doc как
  отдельная история (см. mem feedback_provider_mono_pr_flow).
- scripts/debug-*: вспомогательные скрипты для портал-структуры и
  chairman onboarding'а.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* feat(docs-harness/08): chairman install wizard на partner-dev

Сценарий 08 проходит установочный wizard /:coopname/install целиком:
шаг 1 (RequestKeyForm: WIF partner1 из state/cooperatives/partner1.json),
шаг 2 (SetInitForm: readonly orgdata из is_server_init=true, «Далее»),
шаг 3 (SetSovietForm: один председатель — Иванов И.И.),
шаг 4 (SetVariablesForm: ОПФ+ во всех падежах, устав, конф.email).

Финальный submit «Завершить установку» сейчас падает on-chain в
soviet::create — `assertion: Один из аккаунтов не найден в реестре
пайщиков`. Причина: в install.interactor.ts adduser и createBoard
шлются двумя отдельными tx; partner1 nodeos не producer, между tx есть
лаг p2p-репликации, createBoard приходит до того как participants[N]
обновился. Шот 06-error-state снимается при таймауте; шот
06-completed появится после фикса race в install.interactor (отдельный
коммит).

Сценарий запускается:

  BASE_URL=https://partner-dev.coopenomics.world COOPNAME=partner1 \
  node run.mjs onboarding/08-chairman-install-on-partner-dev

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* fix(controller/install): bundle adduser+createBoard в одну tx

Cause. install.interactor.ts шлёт adduser×N и createBoard двумя отдельными
tx через BlockchainService. На production-нодах с producer-схемой это
работает (lag реплицирования минимальный), но на dev-loop'е partner-
coopback соединён со своим nodeos, который p2p-репликой подтягивает
блоки от producer'а — после accept'а adduser в local state ещё нет
soviet::participants[username] к моменту push'а createBoard. Контракт
soviet::createboard падает «Один из аккаунтов не найден в реестре
пайщиков».

Fix. Объединил все adduser-action'ы и createBoard-action в одну tx
через новый метод BlockchainPort.installSoviet(). Обе action'ы теперь
атомарны в одном блоке — soviet::addpartcpnt (inline action от
adduser) обновляет participants и createBoard видит запись сразу же
в том же блоке.

Поток в install.interactor.ts перестроен в два шага:
  1. Цикл по soviet: createUser в БД + setupNotificationSubscriber +
     сбор addUserActions[] и members[] (без on-chain активности).
  2. installSoviet(addUserActions, createBoardData) — одна tx.

Catch при ошибке on-chain (как и раньше) откатывает users из БД.

Зачем. Закрывает блокер сценария 08-chairman-install-on-partner-dev:
без этого финальный экран wizard'а «Установка завершена» недостижим
на dev-loop'е (Эпик 0 не закрывается).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* feat(docs-harness/09): invite-token → WIF → signin chairman

Закрывает Эпик 0: после сценария 08 (chairman install wizard) на
partner1 в Postgres появляется invite-токен председателя, но Novu не
доставит его на @example.com адрес. Сценарий 09 идёт за токеном
напрямую в БД через `ssh partner1 → docker exec postgres → psql` и
прогоняет до финального signin под новым ключом.

Шаги:
1. fetchLatestInviteToken — SELECT token FROM tokens WHERE
   type='invite' AND blacklisted=false AND expires > NOW() LIMIT 1.
2. Открываем `${BASE_URL}/${COOPNAME}/auth/invite?token=<token>` —
   widget Invite.vue клиентски генерирует новый WIF (generateAccount).
3. Извлекаем WIF из q-input, сохраняем в
   state/cooperatives/partner1-chairman.json для последующих сценариев.
4. Чекбокс «Я сохранил ключ» → «Установить ключ» → resetKey шлёт
   on-chain ChangeKey, фронт редиректит на /auth/signin.
5. Финальный signin под chairman.partner1@example.com + новый WIF;
   ждём перехода на /chairman или /participant.

Запускается:

  BASE_URL=https://partner-dev.coopenomics.world COOPNAME=partner1 \
    node run.mjs onboarding/09-chairman-key-and-login

Требует SSH-доступа к partner1 (PARTNER_SSH=user1@91.218.246.46 по
умолчанию) и предварительно прогнанный сценарий 08 (после merge
fix(controller/install) — иначе токен не появится).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* refactor(controller/install): откатить installSoviet bundle на sleep 2s

Bundle adduser×N + createBoard в одну tx работает, но требует расширения
BlockchainPort и больше read'а; для не-producer-нод (dev-loop) достаточно
короткой паузы между adduser и createBoard, чтобы p2p-реплика подтянула
блок с participants. 2с гарантированно перекрывают и prod (~50ms), и
dev-loop (1-3с).

Отменён 3f2ecc42cf (installSoviet в blockchain.port + blockchain.service +
install.interactor), добавлен `await new Promise(setTimeout, 2000)` между
циклом adduser и createBoard.

Это однострочный фикс race-condition; bundle вернётся когда понадобится
многошаговая атомарность.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* fix(desktop+harness): SPA mode dev + q-checkbox селектор

- desktop dev по умолчанию в SPA — SSR грузит сервер на 70%+ CPU и ломает
  reverse-proxy HTTP/2 multiplex'ом параллельных модулей /src/*. Старый
  режим доступен как `dev:ssr`. docker-compose зовёт `dev` — без правок.
- harness 09: Quasar q-checkbox рендерит label в div, не <label>; кликаем
  по `.q-checkbox:has-text(...)`.

* feat(boot:extra): засев partner1 как coop-пайщика в воскход + announce=domain

В installExtraData (reboot:extra) теперь регистрируется partner1 как
готовый coop-пайщик воскхода со status=active, чтобы dev-стенд после
reboot:extra сразу позволял запустить полный E2E прогон Эпика 0
(provider order_instance → Hostkey rent → playbook → coopback healthy
→ provider initSystem → chairman wizard).

Flow засева:
  newaccount → reguser(type=organization) → regcoop → stcoopstatus(active)
+ Mongo: organization + paymentMethod (bank_account)
+ Postgres: users.partner1{type:organization, role:user, status:joined}

В CooperativeClass — `announce` теперь хранит доменное имя
('voskhod-dev.coopenomics.world'), не текст. Provider читает announce
как domain для DomainDelegationPollingService (regex→is_valid,
health-check L7-Proxy 8880→is_delegated). См. memory
reference_provider_announce_domain.

Без этих правок:
- provider не подхватывает partner1 в свою DB после reboot:extra
- harness 08 после initSystem видит «Unsupported account type:
  undefined» — partner1 organization_data отсутствуют в воскход'е
- announce='Тестовый кооператив' не парсится как domain → is_valid=false

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>

* fix(boot:extra): partner1 reuse WIF из docs-harness фикстуры

В installExtraData boot:extra на каждом запуске генерировал случайный
WIF для partner1 через generateKeypair(undefined). harness 08
(chairman wizard /partner1/install) брал WIF из docs-harness/state/
cooperatives/partner1.json (засеян однократно в репозиторий) — после
reboot:extra on-chain active key уже другой, startInstall mutation на
partner-coopback'е не принимает ключ, wizard зависает на шаге 1 без
видимой ошибки. ACTIVE+initialized провайдером проходит, но
installSystem (создание совета + рассылка инвайт-токенов) не
наступает → harness 09 не может получить WIF chairman'а.

Фикс: если фикстура есть, читаем wif (опц. publicKey, иначе деривим
ecc.privateToPublic) и передаём как seededKeys в generateKeypair —
получается детерминированный partner1 active key, синхронный с
harness'ом. Иначе fallback на старое поведение (рандомный ключ).

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>

---------

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Co-authored-by: coopops <coopops@coopenomics.world>
2026-05-19 22:03:54 +05:00
coopops 9e545329fc chore(contracts): починить .gitignore для собранных контрактов
После переезда контрактов в cpp/ (коммит 2b6b56a, март 2025) паттерны
в components/contracts/.gitignore ссылались на старые пути
(soviet/soviet.wasm и т.п.) и не матчились. В итоге собранные
.wasm/.abi уходили в репозиторий.

— переписаны паттерны на cpp/**/*.{wasm,abi}
— тестовые фикстуры в cpp/tests/test_contracts/** оставлены трекаться
— git rm --cached для soviet.{wasm,abi} и starter.{wasm,abi}
2026-05-19 17:01:46 +00:00
coopops 7ee4cd633f chore: add CLAUDE.md with project-scoped agent notes
Перенёс из общей auto-memory: stack, worktree policy (mono-ai-1 vs mono-ai-4), PR-flow, локальные тесты, GraphQL/desktop каноны, платформенные паттерны (роли, agreements, трёхуровневый онбординг), SDK login, vault & SERVER_SECRET, Capital фиксы, Стол Заказов MVP. Часть реорганизации памяти агента по проектам; в mono-ai-2..5 файл подцепляется локальными симлинками без отдельного коммита (попадёт в feature-ветки при следующем merge от dev).

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-19 16:57:29 +00:00
Alex Ant b973baef03 chore(release): publish
Build bootstrap container / build (push) Failing after 2m59s
2026-05-19 15:59:48 +05:00
Alex Ant e10e049bdd chore(release): publish
Build bootstrap container / build (push) Failing after 2m54s
2026-05-19 14:41:11 +05:00
Alex Ant 8f5fcafecb Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-19 14:40:18 +05:00
Alex Ant bef5df8a06 migration complete 2026-05-19 14:40:02 +05:00
Alex Ant a46a6c173a fix(capital/convertsegm): линковать 1080 к пакету через newlink, не make_complete_document (#409)
PR #403 использовал Soviet::make_complete_document — это вытащило заявление о трансляции (1080)
на верхний уровень реестра как самостоятельный документ. В разделе «Документы» 1080 оказался
отдельной строкой, под ним болтались протокол+акт из соседнего пакета (агрегатор подтягивал их
по тому же result_hash без главного документа).

Правильно — линковать 1080 к существующему пакету процесса p.cap.rid, где ведущим документом
является заявление о внесении РИД (1040, statement из pushrslt). Канон уже есть в signact1/signact2:

  Action::send<newlink_interface>(_soviet, "newlink"_n, _capital, coopname, username,
                                  Names::Capital::SIGN_ACT*_RESULT, result_hash, act);

Здесь по тому же паттерну, action = Names::Capital::CONVERT_SEGMENT (константа уже в dev из #403,
её не трогаем), package = result_hash. Off-chain controller добавит 1080 в группу пакета 1040,
а не на верхний уровень.

verify_document_or_fail оставлен — это безопасность, не связана с проблемой реестра.

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-19 13:51:45 +05:00
Alex Ant 34c4dadec3 feat(capital): требовать допуск для просмотра артефактов проекта/компонента (#407)
Любой авторизованный пользователь раньше мог запросить capitalStories /
capitalStory и получить требования всех проектов кооператива. Закрываем эту
лазейку на бекенде и показываем аккуратную заглушку на фронте.

Backend (controller):
- GenerationService.getStories: фильтрует список разрешённых project_hash
  через PermissionsService. Допуск к корневому проекту каскадно открывает
  все его компоненты; допуск к одному компоненту — только этот компонент.
  Запрос без project_hash/issue_hash доступен только chairman/member.
- GenerationService.getStoryByHash: проверяет допуск через project_hash
  (или issue.project_hash для story с issue_hash) и возвращает null без
  доступа.
- getCapitalStories / getCapitalStory резолверы теперь получают currentUser.
- ProjectPermissionsOutputDTO: добавлены has_parent_clearance и
  can_view_artifacts — для отображения заглушек на фронте.

Frontend (desktop):
- ProjectRequirementsPage / ComponentRequirementsPage: показывают
  ArtifactsAccessPlaceholder когда can_view_artifacts=false, с кнопкой
  получения допуска (или PendingClearanceButton при поданном запросе).
- Новый shared компонент ArtifactsAccessPlaceholder в стиле остальных
  заглушек расширения capital.

SDK:
- projectSelector обновлён под новые поля; schema.gql / zeus
  регенерированы.

Co-authored-by: coopops <coopos@coopenomics.world>
2026-05-19 11:40:37 +05:00
Alex Ant a24f5d4fc1 fix(asset-formatting): truncate (toward-zero) до 2 знаков вместо math-round (#404)
UI показывал баланс 99999.9999 RUB как 100 000,00 — пользователь видел
больше, чем реально на кошельке, и попытка инвестировать «весь баланс»
падала в walletop TRANSFER с insufficient funds (precision=4 на цепи
vs precision=2 в UI).

Принцип: «никогда не показывать сумму больше реальной». Truncate
выполняется на уровне строки, без преобразования в Number, чтобы
избежать FP-погрешности (0.29 * 100 = 28.999... в IEEE 754).

Изменения:
- desktop: новая утилита floorDecimalString — единый источник истины.
- desktop: formatAsset2Digits / formatToAsset / addAssets используют floor.
- desktop: убран double-formatting amount.toFixed(4) перед formatAsset2Digits
  в ParticipantWalletsPage.
- factory: Factory.formatAsset / Factory.formatShare через приватный
  truncateDecimal — тот же принцип в документах (заявления, акты).

Не затронуто (отдельный фолоу-ап): 10 файлов с inline .toFixed(4)
перед отправкой в контракт — рекомендую заменить на formatToAsset().

Co-authored-by: coopops <coopos@coopenomics.world>
2026-05-18 23:41:17 +05:00
Alex Ant 402783d8ae feat(epic-0): onboarding harness 01-08 + install bundle adduser+createBoard в одну tx (#398)
* fix(controller): IS_UNIONED zod-парсер принимает string из .env

z.boolean().default(true) валится для переменной из .env, потому что
process.env всегда отдаёт строку: zod не приводит "true"/"false" к
boolean, в результате validateEnv падает с «IS_UNIONED: параметр не
установлен» и coopback не стартует, если в .env стоит IS_UNIONED=false
(стандартный dev-обход messenger-гейта, см. flow подключения партнёра).

Заменено на string().default('true').transform(v => v === 'true') —
сохранение прежнего default=true и поддержка string-форм из env.

* feat(epic-0): partner onboarding harness — signin → sign agreements → connect

Что добавлено:
- desktop/quasar.config.cjs: vite server.allowedHosts для voskhod-dev/
  partner-dev/api-dev (Vite 5.4+ блокирует cross-origin Host без явного
  списка — иначе SSR/HMR-сервер возвращает 403 «Blocked request»).
- docs-harness/lib/harness.mjs: helper signOnboardingAgreements —
  реальная подпись каскада SignAgreementDialog (wallet/signature/
  privacy/user), каждый клик отправляет sendAgreement → wallet::signagree
  on-chain. В отличие от dismissOnboardingDialogs делает on-chain эффект
  (см. inc 2026-05-18: stale vault SERVER_SECRET → bad decrypt).
- scenarios/onboarding/01..07: новый partner-flow Эпика 0 — partner1
  заходит в Восход, подписывает 4 типовых соглашения, идёт на «Подключение»,
  ant одобряет, наблюдаем установку partner-dev.
- scenarios/registration/01..04: архив старого registration-doc как
  отдельная история (см. mem feedback_provider_mono_pr_flow).
- scripts/debug-*: вспомогательные скрипты для портал-структуры и
  chairman onboarding'а.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* feat(docs-harness/08): chairman install wizard на partner-dev

Сценарий 08 проходит установочный wizard /:coopname/install целиком:
шаг 1 (RequestKeyForm: WIF partner1 из state/cooperatives/partner1.json),
шаг 2 (SetInitForm: readonly orgdata из is_server_init=true, «Далее»),
шаг 3 (SetSovietForm: один председатель — Иванов И.И.),
шаг 4 (SetVariablesForm: ОПФ+ во всех падежах, устав, конф.email).

Финальный submit «Завершить установку» сейчас падает on-chain в
soviet::create — `assertion: Один из аккаунтов не найден в реестре
пайщиков`. Причина: в install.interactor.ts adduser и createBoard
шлются двумя отдельными tx; partner1 nodeos не producer, между tx есть
лаг p2p-репликации, createBoard приходит до того как participants[N]
обновился. Шот 06-error-state снимается при таймауте; шот
06-completed появится после фикса race в install.interactor (отдельный
коммит).

Сценарий запускается:

  BASE_URL=https://partner-dev.coopenomics.world COOPNAME=partner1 \
  node run.mjs onboarding/08-chairman-install-on-partner-dev

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* fix(controller/install): bundle adduser+createBoard в одну tx

Cause. install.interactor.ts шлёт adduser×N и createBoard двумя отдельными
tx через BlockchainService. На production-нодах с producer-схемой это
работает (lag реплицирования минимальный), но на dev-loop'е partner-
coopback соединён со своим nodeos, который p2p-репликой подтягивает
блоки от producer'а — после accept'а adduser в local state ещё нет
soviet::participants[username] к моменту push'а createBoard. Контракт
soviet::createboard падает «Один из аккаунтов не найден в реестре
пайщиков».

Fix. Объединил все adduser-action'ы и createBoard-action в одну tx
через новый метод BlockchainPort.installSoviet(). Обе action'ы теперь
атомарны в одном блоке — soviet::addpartcpnt (inline action от
adduser) обновляет participants и createBoard видит запись сразу же
в том же блоке.

Поток в install.interactor.ts перестроен в два шага:
  1. Цикл по soviet: createUser в БД + setupNotificationSubscriber +
     сбор addUserActions[] и members[] (без on-chain активности).
  2. installSoviet(addUserActions, createBoardData) — одна tx.

Catch при ошибке on-chain (как и раньше) откатывает users из БД.

Зачем. Закрывает блокер сценария 08-chairman-install-on-partner-dev:
без этого финальный экран wizard'а «Установка завершена» недостижим
на dev-loop'е (Эпик 0 не закрывается).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* feat(docs-harness/09): invite-token → WIF → signin chairman

Закрывает Эпик 0: после сценария 08 (chairman install wizard) на
partner1 в Postgres появляется invite-токен председателя, но Novu не
доставит его на @example.com адрес. Сценарий 09 идёт за токеном
напрямую в БД через `ssh partner1 → docker exec postgres → psql` и
прогоняет до финального signin под новым ключом.

Шаги:
1. fetchLatestInviteToken — SELECT token FROM tokens WHERE
   type='invite' AND blacklisted=false AND expires > NOW() LIMIT 1.
2. Открываем `${BASE_URL}/${COOPNAME}/auth/invite?token=<token>` —
   widget Invite.vue клиентски генерирует новый WIF (generateAccount).
3. Извлекаем WIF из q-input, сохраняем в
   state/cooperatives/partner1-chairman.json для последующих сценариев.
4. Чекбокс «Я сохранил ключ» → «Установить ключ» → resetKey шлёт
   on-chain ChangeKey, фронт редиректит на /auth/signin.
5. Финальный signin под chairman.partner1@example.com + новый WIF;
   ждём перехода на /chairman или /participant.

Запускается:

  BASE_URL=https://partner-dev.coopenomics.world COOPNAME=partner1 \
    node run.mjs onboarding/09-chairman-key-and-login

Требует SSH-доступа к partner1 (PARTNER_SSH=user1@91.218.246.46 по
умолчанию) и предварительно прогнанный сценарий 08 (после merge
fix(controller/install) — иначе токен не появится).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* refactor(controller/install): откатить installSoviet bundle на sleep 2s

Bundle adduser×N + createBoard в одну tx работает, но требует расширения
BlockchainPort и больше read'а; для не-producer-нод (dev-loop) достаточно
короткой паузы между adduser и createBoard, чтобы p2p-реплика подтянула
блок с participants. 2с гарантированно перекрывают и prod (~50ms), и
dev-loop (1-3с).

Отменён 3f2ecc42cf (installSoviet в blockchain.port + blockchain.service +
install.interactor), добавлен `await new Promise(setTimeout, 2000)` между
циклом adduser и createBoard.

Это однострочный фикс race-condition; bundle вернётся когда понадобится
многошаговая атомарность.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Co-authored-by: coopops <coopops@coopenomics.world>
2026-05-18 23:31:54 +05:00
Alex Ant 2479cce94d fix(capital/convertsegm): регистрировать convert_statement в реестре документов как completed (#403)
Build bootstrap container / build (push) Failing after 2m54s
Финальная фаза процесса p.cap.rid (convertsegm) принимала document2 convert_statement (шаблон 1080)
параметром, но:

1. **Не проверяла подпись** — `verify_document_or_fail` отсутствовала, поэтому on-chain
   принял бы любую сконструированную document2 без валидной user-подписи.
   У signact1/signact2 (соседние фазы того же процесса) verify есть — здесь забыли.

2. **Не регистрировала документ в реестре** — `newlink`/`newsubmitted`/`newresolved`
   не вызывался, заявление о трансляции 1080 «терялось»: off-chain controller (process_instance)
   не видел финальный документ привязанным к result_hash, процесс p.cap.rid не помечался completed.
   У pushrslt (create_approval) и signact2 (newlink с SIGN_ACT2_RESULT) линковка есть.

Канон есть в soviet/src/system/converttoaxn.cpp:54 и soviet/src/agreement/sndagreement.cpp:104:
паттерн `Soviet::make_complete_document(calling_contract, coopname, username, action, package_hash, document)`
шлёт newsubmitted + newresolved одной парой, package = анкер процесса (здесь result_hash).

Изменено:
- names.hpp: новая константа Names::Capital::CONVERT_SEGMENT = "convertsegm"_n (12 символов)
- convertsegm.cpp:
  - verify_document_or_fail(convert_statement, {username}) сразу после require_auth
  - Soviet::make_complete_document(...) ДО delete_result (чтобы линковка прошла, пока result_hash ещё анкер)

Контракт capital собирается без ошибок (cdt-cpp testnet mode), warnings — старые ricardian.

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-18 22:47:38 +05:00
Alex Ant bd0bd21ae7 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-18 22:03:29 +05:00
Alex Ant abcd34f23d fix(capital): revert ошибочной замены GenerationConvertStatement → MoneyInvestStatement (#394) (#396)
PR #394 «починил» TS-ошибки coopback заменой типа `Cooperative.Registry.GenerationConvertStatement`
на `GenerationMoneyInvestStatement` в 3 файлах controller'а. Это семантически неверно:

- 1080 GenerationConvertStatement — заявление о трансляции паевого взноса
  (поля: project_hash, main_wallet_amount, blagorost_wallet_amount, to_wallet, to_blagorost, appendix_hash)
- 1020 GenerationMoneyInvestStatement — заявление о денежном паевом взносе по программе Генерация
  (совсем другой набор полей)

DTO BaseGenerationConvertStatementMetaDocumentInputDTO декларирует поля 1080, но `implements ExcludeCommonProps<action>`
где action = тип 1020 → TS2352 на as-cast в interactor, потому что Action'ы не пересекаются по полям.

Реальная причина исходных ошибок coopback после #392 — несвежий dist `@coopenomics/cooptypes`
на dev-узле (старое имя символа). Лечится пересборкой пакета, не переименованием ссылок.

Изменено (откат #394):
- generation-convert-statement-document.dto.ts:12 — `action = ...GenerationConvertStatement.Action`
- distribution-management.service.ts:56 — `registry_id: ...GenerationConvertStatement.registry_id`
- distribution-management.interactor.ts:48,66 — `Promise<...GenerationConvertStatement.Action>`

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-18 13:00:45 +05:00
Alex Ant 83cac58fca fix(controller): IS_UNIONED zod-парсер принимает string из .env (#395)
z.boolean().default(true) валится для переменной из .env, потому что
process.env всегда отдаёт строку: zod не приводит "true"/"false" к
boolean, в результате validateEnv падает с «IS_UNIONED: параметр не
установлен» и coopback не стартует, если в .env стоит IS_UNIONED=false
(стандартный dev-обход messenger-гейта, см. flow подключения партнёра).

Заменено на string().default('true').transform(v => v === 'true') —
сохранение прежнего default=true и поддержка string-форм из env.

Co-authored-by: coopops <coopos@coopenomics.world>
2026-05-18 12:40:57 +05:00
Alex Ant dbf46d88d0 fix(capital): подтянуть 3 ссылки на GenerationConvertStatement → MoneyInvestStatement (#394)
PR #392 переименовал Cooperative.Registry.GenerationConvertStatement в
GenerationMoneyInvestStatement в @coopenomics/document, но в controller
осталось 3 несинхронизированные ссылки:

- distribution-management.service.ts:56 — registry_id метода generation
- distribution-management.interactor.ts:48,66 — тип Action в return и as-cast
- generation-convert-statement-document.dto.ts:12 — type action в DTO

Coopback падал на ts-node compile (TS2551/2724), что блокировало старт
всего dev-stack после reboot dev-chain 2026-05-18.

Co-authored-by: coopops <coopos@coopenomics.world>
2026-05-18 12:29:32 +05:00
Alex Ant a0cb930b77 refactor(capital/convert): унифицировать шаблон 1080, убрать 1081/1082 (#392)
* refactor(capital/convert): унифицировать 1080 как универсальное заявление о конвертации, убрать 1081/1082

Шаблон 1080 (GenerationConvertStatement) уже технически универсален — содержит
обе суммы (main_wallet_amount/blagorost_wallet_amount) и условные блоки в
context. Шаблоны 1081 (GenerationToProjectConvertStatement) и 1082
(GenerationToCapitalizationConvertStatement) были недоделанными заглушками
без полей и нигде не подключены в UI.

Изменения:
- cooptypes: 1080 переименован GenerationToMainWalletConvertStatement →
  GenerationConvertStatement; title/description нейтральные. 1081/1082 удалены.
- factory: Template + Action 1080 переименованы; в Action добавлено
  super.formatAsset(...) для обеих сумм (как в Action 1020). 1081/1082 удалены.
- controller: DTO переименован; appendix_hash убран из generate-input и
  перенесён в signed-meta-input; добавлен enrich appendix_hash через
  AppendixRepository.findConfirmedByUsernameAndProjectHash в
  DistributionManagementInteractor.prepareGenerationConvertStatementData
  (по образцу InvestsManagementInteractor для 1020). Резолвер мутации
  переименован в capitalGenerateGenerationConvertStatement; убраны два
  резолвера 1081/1082. mutation-log-mapper обновлён.
- sdk: мутация переименована, две удалены, zeus regenerated.
- desktop: Distribution-фичи 1081/1082 удалены, 1080-фича переименована.
  ConvertSegment теперь шлёт project_hash + обе суммы (formatToEosioAsset) +
  to_wallet/to_blagorost; appendix_hash подтягивается на бекенде.
- controller schema.gql regenerated.

registry_id=1080 не меняется — on-chain контракт convertsegm не сверяет
registry_id, миграций БД/контракта не требуется.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* refactor(capital/convert): применить ревью — title «трансляция паевого взноса из программы Генерация»

По комментарию ревью в PR #392 (строка 37): принять доменный термин
«трансляция паевого взноса» (перенос между программами) вместо
«конвертация»; description согласован в том же стиле.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-18 11:29:12 +05:00
Alex Ant 4a4145c4ed feat(controller): is_server_init флаг в initSystem для provider-overwrite (#391)
* feat(docs-harness): onboarding 01..06 — визуальная цепочка регистрация → активация

Шесть сценариев visual docs-harness, покрывающих полный путь подключения
нового кооператива через провайдера Восход:

  01-register-coop                 — регистрация кооператива-клиента
  02-sign-and-submit               — подпись заявления о вступлении + PayInitial
  03-operator-approve              — chairman принимает заявку в реестре одобрений
  04-sign-connection-agreement     — Партнёр-1 видит ConnectionAgreementStepper
                                     (на текущем стенде получаем заглушку
                                     /signup, пока пайщик не принят)
  05-activate-from-registry        — оператор открывает карточку инстанса
                                     в provider-frontend, выбирает preset
  06-wait-instance-active          — pending → ACTIVE (overrideInstance
                                     для имитации финального статуса в шоте)

Обвязка:
  • lib/registrator-signup.mjs — переиспользуемый helper подписания.
  • lib/harness.mjs — расширенный dismissOnboardingDialogs (Положение ЦПП
    и связанные модалки chairman'а).
  • state/cooperatives/{,.gitkeep} — папка для фикстур; partner1.json
    (с приватным wif) игнорируется (.gitignore обновлён).

ОГРАНИЧЕНИЕ: в 06 финальный ACTIVE — это playwright-override JSON, а не
реальный POST /instances/activate с боевым Ansible до testnet300.coopenomics.world.
Реальный E2E (аренда VM на Hostkey + поднятие кооператива на домене)
будет следующим шагом Эпика 0.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>

* feat(controller): is_server_init flag в initSystem для разблокировки provider-overwrite

Поле data.is_server_init: boolean (optional) в InitDTO + домейн-интерфейсе.
Если true (вызов от провайдера через server-secret) — coopback ставит
init_by_server=true безусловно, даже если до этого пользователь успел
заполнить визард первым (user-init). Это разблокирует ситуацию, когда
провайдер не успел вызвать initSystem до того как chairman открыл
/install — следующий callInitSystemMutation от провайдера перезапишет
organization_data и пометит её readonly для визарда.

Без флага сохраняется прежняя логика: первая инициализация — серверная,
повторная наследует флаг.

Инцидент 2026-05-18 на partner1: при первой установке provider вообще
не успел/не сходил в callInitSystemMutation, визард пользователя
проинициализировал систему как user-init (init_by_server=false), визард
2-го захода не предзаполнил форму. С этим фиксом следующий вызов
provider'а поднимет флаг и фикстура встанет на место.

---------

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-18 10:40:49 +05:00
Alex Ant d35ec2680a chore(release): publish
Build bootstrap container / build (push) Failing after 2m51s
2026-05-15 22:28:10 +05:00
Alex Ant 8523ab0c08 Merge branch 'testnet' 2026-05-15 22:27:55 +05:00
Alex Ant 74e3e88853 chore(release): publish
Build bootstrap container / build (push) Failing after 3m5s
2026-05-15 22:23:44 +05:00
Alex Ant 36441437db Merge branch 'dev' into testnet 2026-05-15 22:22:59 +05:00
Alex Ant 00860b3b18 fix commit process
Build bootstrap container / build (push) Failing after 2m52s
2026-05-15 22:21:35 +05:00
Alex Ant 8fe9509e97 fix(capital/time-tracking): личные доли estimate + revert при decline (#387)
* chore(release): publish

* chore(release): publish

* ci: атомарный release.yaml, убрать workflow_run-связку (#366)

build-contracts + build-containers через workflow_run упёрлись в:
(а) default-branch caveat (новая логика не активна, пока не в main),
(б) `${{ github.event.workflow_run.head_sha }}` иногда пуст в YAML-
выражениях — описание см. в шаге Resolve tag, инцидент v2026.5.14
не дёрнул PRODUCTION_WEBHOOK_URL.

Замена — один `release.yaml` на push тэга `v*`: резолвит ветку через
`git branch --contains`, собирает контракты → пушит
`dicoop/contracts:<branch>`, собирает базу + сервисные образы →
пушит `dicoop/<svc>:<tag>`, шлёт webhook. Гонок нет by construction.

`build-contracts.yaml` остаётся только на push веток для CI-
обновления `dicoop/contracts:dev|testnet|main` без релизного тэга.
Триггер `tags: ['*']` и логика резолва ветки через --contains
оттуда удалены — это теперь забота release.yaml.

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>

* chore(release): publish

* chore(release): publish

* ci: tag-only триггеры для build-contracts и docs (#367)

build-contracts.yaml — только workflow_dispatch (ручная пересборка
`dicoop/contracts:<branch>` для отладки на dev-ноде). Тэги обрабатывает
release.yaml атомарно (контракты + контейнеры + webhook), отдельная
сборка по push'у в ветку только давала вторую параллельную сборку.

publish-docs.yaml и build-contracts-docs.yaml — на push:tags v* с
gate-job'ом, пропускающим только продакшн-тэги (без -alpha/-beta/-rc/
-test) на main. Раньше docs пересобирались на каждый push в
main/testnet/dev/reports/marketplace2 — впустую.

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>

* fix(capital/time-tracking): личные доли estimate, partial-split, revert при decline

Три бага в распределении билетов времени, вскрытые на прод-инциденте voskhod
(проект CC7-1 «Концепция», estimate=15 ч, 3 creators):

БАГ #1 — recalcDoneEstimatesForContributorProject раздавал «общий остаток пула»
(estimate − committed_total) / N всем creators поровну. Закоммитивший свою долю
получал её ещё раз, остальные — урезанную (15/3=5 → после committed 5 у одного
становилось 10/3=3.33 у каждого, включая того кто уже закоммитил).

Фикс: личная доля = estimate/N − собственный committed estimate. Введён общий
helper redistributeIssueEstimateEntries, который используют и applyExplicit-
EstimateToTimeEntries (force=true), и recalcDoneEstimates (force=false с
no-op оптимизацией если раскладка уже совпадает с планом).

БАГ #2 — commitTime при partial split (entry.hours > requested) создавал новую
committed-запись без entry_type и estimate_snapshot. По default'у БД сохраняла
её как entry_type='hourly', что ломало последующий recalc (он фильтрует только
entry_type='estimate'). Фикс: явно копировать entry_type и estimate_snapshot
из оригинального entry.

БАГ #3 — declineCommit / handleDeclineCommit меняли только commit.status в БД,
но не возвращали time-entries в is_committed=false. После отказа мастера часы
оставались в total_committed_hours и не возвращались в available_hours. Фикс:
новый метод revertEntriesForDeclinedCommit в TimeTrackingInteractor + методы
findCommittedByCommitHash / revertCommittedEntriesByCommitHash в TimeEntry-
Repository. После revert делается force=true redistribute для затронутых DONE
задач, чтобы доли вернулись в норму.

Покрытие тестами: 17 unit-тестов в time-tracking.interactor.spec.ts с
регрессионными сценариями под каждый из трёх багов плюс integration-сценарий
полного lifecycle CC7-1 (estimate → коммит → decline → revert).

---------

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-15 22:02:36 +05:00
Alex Ant 43a9e05ccb chore(release): publish
Build bootstrap container / build (push) Failing after 2m55s
2026-05-15 17:20:43 +05:00
Alex Ant d4de7a3028 Merge branch 'testnet' 2026-05-15 16:48:30 +05:00
Alex Ant e2584fb898 chore(release): publish
Build contracts container / build (push) Failing after 2m54s
Build bootstrap container / build (push) Failing after 2m53s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 7s
Publish Docs / build-and-publish-docs (push) Failing after 18m43s
2026-05-15 16:39:03 +05:00
Alex Ant 3785c55af1 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-15 16:38:35 +05:00
coopops 848566bd69 fix(file-storage): MinIO стартует только при заданном MINIO_ENDPOINT
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 11s
Publish Docs / build-and-publish-docs (push) Failing after 18m20s
Раньше MINIO_ENDPOINT имел default http://minio:9000, и на проде без
minio-контейнера контроллер падал на bootstrap в HeadBucket с
getaddrinfo ENOTFOUND minio — Nest application не поднимался вообще.

Теперь MINIO_ENDPOINT optional без default; адаптер хранит enabled-флаг
по наличию endpoint и при отсутствии — onApplicationBootstrap логирует
warning и возвращается без сетевых вызовов. Любая попытка getBucket /
fetchObjectForReadProxy кидает InterFileStorageBackendUnavailableError
с понятным сообщением.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-15 11:30:48 +00:00
Alex Ant 61255da5f4 Merge branch 'main' of github.com:coopenomics/mono 2026-05-15 16:26:18 +05:00
Alex Ant 1a63638f73 chore(release): publish 2026-05-15 15:45:18 +05:00
Alex Ant c8bc5c782d fix commit process 2026-05-15 15:44:46 +05:00
Alex Ant 4e2fbac340 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-15 15:44:28 +05:00
coopops aeb4efe2b6 fix(capital/commit): nullable description/meta в CommitOutputDTO + не дефолтить satisfaction в 5
Если syncCommit не дождался delta из блокчейна, interactor возвращает DB-only
entity, где description/meta остаются undefined — non-nullable GraphQL field
ломал ответ мутации capitalCreateCommit. Сделал оба поля nullable.

UI CreateCommitButton.vue: satisfaction_stars=0 по умолчанию, label "не указано"
пока пользователь не выбрал; блок contribution_feedback в payload только если
stars >= 1 или review_text непустой.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-15 10:43:12 +00:00
Alex Ant 7ef138ba19 feat(file-storage): универсальное файловое хранилище контура кооператива (MinIO/S3-портабельное) (#359)
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 7s
Publish Docs / build-and-publish-docs (push) Failing after 17m11s
* [E59-2][@ant] feat(inter): InterFileStorage порт — типы, токен INTER_FILE_STORAGE и типизированные ошибки для универсального файлового хранилища контура кооператива

* [E59-3][@ant] feat(controller): MinIO-адаптер InterFileStoragePort, реестр бакетов, @UseBucket/@InjectBucket декораторы и FileStorageInfrastructureModule с forRoot/forFeature; 36 unit-тестов на адаптер, реестр, декоратор и HMAC-подписание

* [E59-4][@ant] feat(controller): HTTP-ручка GET /api/storage/:bucket/:key с HMAC-валидацией подписи и стримом из MinIO; fetchObjectForReadProxy на адаптере, controller registered в FileStorageInfrastructureModule.forRoot; 9 e2e-тестов через supertest на 200/403/404/502

* [E59-5][@ant] test(controller): integration suite против реального MinIO — 8 сценариев на полный цикл put/head/getReadUrl/GET/delete + ошибки лимитов/MIME/metadata + HMAC-роут 200/403/404; docker-compose рядом с тестами, npm run test:integration:file-storage с автодетектом доступности MinIO

* [E59-6][@ant] feat(controller,compose): MinIO в dev docker-compose, env-валидация и FileStorageInfrastructureModule.forRoot в app.module — контроллер на старте идемпотентно создаёт бакет coop-<coopname>; integration-тесты проходят против MinIO из dev compose

* [E59-6][@ant] docs(file-storage): краткий README для разработчиков расширений — пример @UseBucket/@InjectBucket/forFeature, операции, ошибки, env, как запускать тесты

---------

Co-authored-by: coopops <coopos@coopenomics.world>
2026-05-14 23:14:10 +05:00
Alex Ant 8aeee3ee56 ci: tag-only триггеры для build-contracts и docs (#367)
Build bootstrap container / build (push) Failing after 2m56s
build-contracts.yaml — только workflow_dispatch (ручная пересборка
`dicoop/contracts:<branch>` для отладки на dev-ноде). Тэги обрабатывает
release.yaml атомарно (контракты + контейнеры + webhook), отдельная
сборка по push'у в ветку только давала вторую параллельную сборку.

publish-docs.yaml и build-contracts-docs.yaml — на push:tags v* с
gate-job'ом, пропускающим только продакшн-тэги (без -alpha/-beta/-rc/
-test) на main. Раньше docs пересобирались на каждый push в
main/testnet/dev/reports/marketplace2 — впустую.

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-14 14:58:24 +05:00
Alex Ant 70446c300d chore(release): publish 2026-05-14 13:59:19 +05:00
Alex Ant 007a4dbfb8 Merge branch 'main' of github.com:coopenomics/mono 2026-05-14 13:59:05 +05:00
Alex Ant 582a2825be chore(release): publish
Build bootstrap container / build (push) Failing after 2m45s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 4s
Publish Docs / build-and-publish-docs (push) Failing after 14m42s
2026-05-14 13:58:25 +05:00
Alex Ant b2f13dc093 ci: атомарный release.yaml, убрать workflow_run-связку (#366)
build-contracts + build-containers через workflow_run упёрлись в:
(а) default-branch caveat (новая логика не активна, пока не в main),
(б) `${{ github.event.workflow_run.head_sha }}` иногда пуст в YAML-
выражениях — описание см. в шаге Resolve tag, инцидент v2026.5.14
не дёрнул PRODUCTION_WEBHOOK_URL.

Замена — один `release.yaml` на push тэга `v*`: резолвит ветку через
`git branch --contains`, собирает контракты → пушит
`dicoop/contracts:<branch>`, собирает базу + сервисные образы →
пушит `dicoop/<svc>:<tag>`, шлёт webhook. Гонок нет by construction.

`build-contracts.yaml` остаётся только на push веток для CI-
обновления `dicoop/contracts:dev|testnet|main` без релизного тэга.
Триггер `tags: ['*']` и логика резолва ветки через --contains
оттуда удалены — это теперь забота release.yaml.

Co-authored-by: coopops <coopos@coopenomics.world>
Co-authored-by: Claude Opus 4.7 <noreply@anthropic.com>
2026-05-14 13:55:04 +05:00
Alex Ant c41aba12f1 chore(release): publish
Build bootstrap container / build (push) Failing after 2m58s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 6s
Build contracts container / build (push) Failing after 9m28s
Publish Docs / build-and-publish-docs (push) Failing after 16m1s
2026-05-14 10:53:46 +05:00
Alex Ant 5a01aee69f chore(release): publish
Build bootstrap container / build (push) Failing after 2m55s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 6s
Publish Docs / build-and-publish-docs (push) Failing after 15m39s
Build contracts container / build (push) Failing after 9m4s
2026-05-13 22:40:40 +05:00
Alex Ant e6880e149b Merge branch 'dev' of github.com:coopenomics/mono into dev
Build bootstrap container / build (push) Failing after 2m53s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 6s
Build contracts container / build (push) Failing after 9m8s
Publish Docs / build-and-publish-docs (push) Failing after 15m25s
2026-05-13 22:40:12 +05:00
coopops a9c1e1924a ci: workflow_dispatch fallback для build-containers
После переключения build-containers с `push: tags` на `workflow_run`
обнаружился разрыв в миграционный период: на default-ветке (main) лежит
старый build-containers (с `push: tags`), на dev/testnet — уже новый
(с `workflow_run`). Push релизного тэга на коммит из dev/testnet НЕ
триггерит:
- старый build-containers в main: GitHub читает workflow definition
  ИЗ КОММИТА тэга (где уже новая версия без `push: tags`);
- новый build-containers через workflow_run: триггер берётся из
  default-ветки, где ещё старая версия без `workflow_run`.

В итоге для тэгов v2026.5.13-alpha-2/-3 build-containers не запустился
вовсе.

Фикс: workflow_dispatch с input.tag — позволяет руками запустить
сборку+деплой для любого выпущенного тэга. Логика resolve_tag
поддерживает оба источника. Это снимает блокер до мержа в main.

Использование:
  gh workflow run "Build Docker Images" -f tag=v2026.5.13-alpha-3
2026-05-13 17:37:55 +00:00
Alex Ant 938c3ff042 chore(release): publish 2026-05-13 21:44:14 +05:00
Alex Ant cd9ab32f04 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-13 21:43:52 +05:00
coopops 47f616e980 fix(ci/build-contracts): резолвить branch при триггере по тэгу
После коммита 5735e1fc36 workflow стал триггериться на push тэгов,
но `Determine build mode and docker tag` использовал `github.ref_name`
напрямую, который для тэга = `v2026.5.13-alpha-2` → не матчит ни одну
из ветвей в `case` → workflow падает «Unsupported branch».

Фикс: для триггера по тэгу резолвим ветку через `git branch -r --contains
$SHA` (порядок: main → testnet → dev). Полная история нужна для
`--contains`, поэтому checkout с `fetch-depth: 0`. Семантику
build-режима несёт ветка, не имя тэга.
2026-05-13 16:40:09 +00:00
Alex Ant 908349ac67 chore(release): publish 2026-05-13 21:36:49 +05:00
Alex Ant 64f8201eb6 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-13 21:36:30 +05:00
coopops 5735e1fc36 ci: build-containers зависит от build-contracts через workflow_run
Раньше при релизе (`chore(release): publish` + git tag) запускались
параллельно `build-contracts.yaml` (push веток) и `build-containers.yaml`
(push тэгов). Поскольку контейнеры собираются ~8 минут, а контракты ~11,
build-containers финишил первым и слал webhook на тестнет за 2-3 минуты
до того, как build-contracts успевал запушить новый `dicoop/contracts:dev`
в DockerHub. Ансибл `setup-contracts.yaml` подтягивал ПРЕДЫДУЩИЙ образ
и через `cleos set contract` перетирал чейн старым wasm.

Инцидент 2026-05-13: walletop-фикс ledger2 (коммит 2e3410b830),
вручную задеплоенный 12-05, был откачен ансиблом ровно по этой
причине — ансибл подтянул контракты сборки 12-05 04:54 (sha de0f6c79,
до моего фикса).

Изменения:
- `build-contracts.yaml` дополнительно триггерится на push любого тэга
  (без path-фильтра): нужен unconditional запуск, чтобы у workflow_run
  всегда был upstream-завершение даже когда коммит ничего не правит
  в `components/contracts/cpp/**`.
- `build-containers.yaml` переключён с `push: tags` на `workflow_run:
  Build contracts container completed`. Внутри: резолв тэга через
  `git describe --tags --exact-match $head_sha` — если на коммите тэга
  нет (обычный push в ветку без релиза), no-op. Если есть — собирает
  контейнеры и шлёт webhook ровно как раньше, но с гарантией что
  `dicoop/contracts:<branch>` уже свежий.

Важно: workflow_run-триггер берёт definition из default-ветки (main),
поэтому новый build-containers.yaml начнёт работать только после мержа
этого коммита в main. До тех пор сохраняется старое поведение dev-ветки
(workflow_run от build-contracts на dev запустит build-containers из
main; если там старая версия — всё ещё через push: tags).
2026-05-13 16:24:12 +00:00
Alex Ant 4a6aa8c447 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-13 20:45:03 +05:00
coopops b2a304e9de test(controller/capital): синхронизировать ассерт под applicable_account_types: []
Build bootstrap container / build (push) Failing after 2m52s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 11s
Build contracts container / build (push) Failing after 11m30s
Publish Docs / build-and-publish-docs (push) Failing after 19m16s
В коммите 8847a5c093 production-код registerCapitalInAgreementRegistry
изменил applicable_account_types у blagorost_offer на [] — оферта
тянется через программу CAPITALIZATION, а не как дефолт для individual.
Тест capital-plugin-register.test.ts остался на ассерте
[AccountType.individual] и с тех пор красный.

Выравниваю ассерт под актуальное поведение, удаляю ставший лишним
импорт AccountType.
2026-05-13 15:38:59 +00:00
coopops 6eeb4567b1 fix(controller/capital): BLAGOROST_AGREEMENT_TYPE = 'capital' (on-chain имя)
В `soviet::coagreements[voskhod]` оферта Благорост (program_id=4)
зарегистрирована под `type='capital'` — и на тестнете, и на проде.
Расширение capital после Эпика 1.3 отвечает за on-chain тип оферты,
но в `capital-agreement-ids.ts` значение `'blagorost'` унаследовано
из старого ядерного `AgreementType.CAPITAL`, который, в свою очередь,
был неверно изменён в commit 283af35f3b («looking for access
violation bug»).

Эффект на тестнете: при регистрации любого individual-аккаунта
контроллер шлёт `soviet::sndagreement` с agreement_type='blagorost',
`get_coagreement_or_fail` падает с «Соглашение указанного типа не
найдено», регистрация не завершается.

Возвращаю значение к on-chain имени; обновляю тест и три комментария,
которые декларировали старое значение как канон.
2026-05-13 15:28:31 +00:00
coopops b92abb80a8 fix(ledger2/voskhod): мин.паевые → w.sov.mnused; правка accounts2 (51/08)
migrate_voskhod_facts:
- accounts2[51]: 176 800 → 145 000 (минус 31 800 минП, теперь только деньги)
- accounts2[08]: 543 400 → 575 200 (плюс 31 800 минП — инвестировано в активы)
- accounts2[04/80/86] без изменений; Σ Dr = Σ Cr = 63 073 511 ✓

Новый COOPERATIVE-кошелёк w.sov.mnused для аналитики "использованные
минимальные паевые взносы" (Cr 80 source, перешедшие в 08). Для voskhod
31 800 размещается там вместо w.reg.minshr — обязательство перед пайщиками
на счёте 80 сохранено, но wallet-аналитика отражает что средства уже
ушли в долгосрочные активы.

migrator-048 (Phase 1 L3 → w.reg.minshr): skip voskhod явным if в TS +
жёсткий guard в migrate3 (eosio::check отвергает запись L3(voskhod,
w.reg.minshr) в prod). В testnet-сборке guard выключен — voskhod проходит
стандартный арифметический путь для видимости invariant-фейлов.

Реестр LEDGER2_WALLET_REGISTRY 13 → 14; namespace w.sov.* расширён до
"совет-level фондов" (целевое финансирование + использованные паевые).
TS-зеркало (wallets.generated.ts) регенерировано через pnpm gen:from-cpp;
snapshot-тест cooptypes обновлён.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 15:20:35 +00:00
Alex Ant dcd3c9293a chore(release): publish
Build bootstrap container / build (push) Failing after 2m52s
Trigger Contracts Docs Deploy / trigger-coopenomics (push) Failing after 5s
Build contracts container / build (push) Failing after 2m48s
Publish Docs / build-and-publish-docs (push) Failing after 15m54s
2026-05-13 19:22:44 +05:00
Alex Ant f952be5f83 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-13 19:20:12 +05:00
Alex Ant bd8eb34e43 Merge pull request #365 from coopenomics/onboarding
feat(onboarding): платформенный механизм онбординга кооператива на расширение (issue 549)
2026-05-13 19:19:46 +05:00
coopops 7d9583d862 fix(desktop/session): дашборд и кошелёк — только при status='active'
Промежуточные статусы пайщика (created/joined/payed/registered) больше
не показываются как «уже зарегистрирован». Пайщик с WIF в localStorage,
но без принятия советом, видит публичную главную и кнопки login/register
— как незарегистрированный. Это позволяет ему серфить сайт между шагами
регистрации, не получая преждевременно подпись оферты цифрового кошелька.

Изменения:
- SessionStore.isFullyActive — новый computed, true при user_account.status === 'active'.
- navigation-guard-setup: ветка index выбирает дашборд только для isFullyActive;
  requiresAuth-маршруты при isAuth && !isFullyActive (вне /auth/*) шлёт на index.
- init-wallet: не дёргать wallet.loadUserWallet пока !isFullyActive (account.getAccount
  оставляем — нужен для определения статуса).
- init-app: selectDefaultWorkspace только при isFullyActive (иначе non_authorized).
- Desktop store: ветки в selectDefaultWorkspace / getDefaultPageRoute идут от
  isFullyActive, не isAuth.

Источник истины статуса — миграция V2.2.0 + ParticipantStatusSyncService:
все accepted-пайщики on-chain переводятся в users.status='active' в моно.
Замер на восходе (api.coopenomics.world soviet::participants[scope=voskhod]):
34 accepted + 1 blocked = 35, все «принятые» → ровно active.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-13 13:40:15 +00:00
coopops 8847a5c093 fix(controller/capital): blagorost_offer — только через программу CAPITALIZATION, не дефолт для individual
При выборе программы GENERATION generateRegistrationDocuments падал с
«Данные соглашения благороста не найдены в Udata»: blagorost_offer с
applicable_account_types: [individual] тянулась как дефолтная оферта,
но generateDocumentParameters под GENERATION зовёт только
generateGeneratorOfferParameters → Factory не находит udata для blagorost
→ Promise.all rejected → фронт получает 0 документов → пайщик ничего
не подписывает → backend бракует "Отсутствуют blagorost_offer, generator_offer".

Фикс: applicable_account_types: [] на blagorost_offer. Оферта подтягивается
исключительно через agreement_ids программы CAPITALIZATION (как и generator_offer
через GENERATION).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-13 10:24:04 +00:00
coopops 37b7387830 fix(sdk+desktop/onboarding): vue-tsc types — selector без as any, ComputedRef в интерфейсе
Селектор `extensionOnboardingStateSelector` использовал `as any` на nested-объекте, из-за чего `InputType<...>` терял форму `steps` (резолвился в `unknown`). Убрал `as any` + `as const`, добавил `MakeAllFieldsRequired` валидацию — паттерн как в `commitSelector`.

Composable `useExtensionCooperativeOnboarding` объявлял интерфейс через `ReturnType<typeof computed<T>>`, что резолвится в `WritableComputedRef` (последний overload Vue). Заменил на явные `ComputedRef<T>` / `Ref<T>` — фактическая форма не writable.

Со-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 18:01:52 +00:00
coopops 968990c3ff feat(sdk+desktop/onboarding): SDK regen + features/CooperativeOnboarding (Эпики A3+A4)
SDK:
- Регенерирован zeus-клиент под новые типы ExtensionOnboardingState и
  CompleteExtensionOnboardingStepInput из платформенного резолвера.
- Добавлен namespace `Queries.Onboarding.GetExtensionOnboardingState`,
  `Mutations.Onboarding.CompleteExtensionOnboardingStep` и селектор
  `extensionOnboardingStateSelector`.

Desktop features/CooperativeOnboarding (FSD):
- `useExtensionCooperativeOnboarding(getExtensionName)` — реактивный
  controller со state/steps/allDone/expiresAt + load/completeStep.
- `<CooperativeOnboardingGate extension="...">` — slot-based wrapper:
  пока !all_done показывает `slot[onboarding]` (по дефолту —
  CooperativeOnboardingSteps), после ратификации всех шагов —
  основной слот.
- `<CooperativeOnboardingSteps>` — список шагов с кнопкой "Создать
  предложение совету"; событие `propose` поднимается parent'у для
  открытия формы — UX-форма остаётся за конкретным расширением.

Использование Стол заказов (и любым новым расширением): обернуть
рабочий экран в `<CooperativeOnboardingGate extension="stol_zakazov">`,
шаги показываются автоматически из платформенного реестра.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 16:35:45 +00:00
coopops c32d265bb1 feat(controller/onboarding): платформенный механизм онбординга кооператива на расширение (Эпики A1+A2)
Системный паттерн «онбординг кооператива на расширение»:
- OnboardingStepsRegistry — in-memory реестр шагов, регистрация
  декларативно в initialize() расширения.
- ExtensionOnboardingService — generic getState/completeStep, работает
  с любым extension, шаги задаются спецификацией IExtensionOnboardingStepSpec
  с двумя generator'ами: free_decision (создаёт project + опубликовывает +
  регистрирует tracking-rule SOVIET_DECISION) и meet (registerTrackingRule
  MEET_DECISION с externally-provided proposal_hash).
- ExtensionOnboardingEventsService — generic слушатель DecisionTrackedEvent
  для расширений без legacy events-сервиса (chairman/capital — пропускает).
- GraphQL endpoint getExtensionOnboardingState / completeExtensionOnboardingStep
  с ролевой защитой (query open для chairman/member/user, mutation chairman).

A2: chairman и capital декларативно регистрируют свои существующие шаги
через ONBOARDING_STEP_REGISTRATION_PORT — step_key совпадает с
config-полями onboarding_<step_key>_done/hash, поэтому legacy resolver'ы
и платформенный сходятся на единой истине в config'е.

Capital: step_key='blagorost_provision' выбран под существующее поле
onboarding_blagorost_provision_done (legacy enum использует 'blagorost_program').

Юнит-тесты OnboardingStepsRegistry: регистрация/дубликаты/order/unregister.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 16:27:01 +00:00
coopops a1bee6f630 merge: align worktree base with onboarding branch 2026-05-12 16:18:17 +00:00
coopops 2fd0087e93 feat(desktop/onboarding): features/DocumentSigning — переиспользуемый пакет генерации и подписи (Эпик B1)
Платформенный composable + 2 widget'а для генерации и подписи пачки
документов пайщика. Локальный state (без Pinia) — можно инстанциировать
независимо в любом месте: и в Registrator, и на странице расширения,
онбордящего пайщика по своему flow.

— useDocumentSigning(getOpts) — load() / setAccepted() / signAll() / linkHashes
— <DocumentsChecklist :documents @update:accepted> — чек-лист с ReadAgreementDialog
— <DocumentsSignCanvas @signed> — canvas-подпись, эмитит сигнатуру

Backend генерации (generateRegistrationDocuments mutation +
AgreementRegistry) уже был generic — этот эпик закрывает фронтенд-сторону.

Registrator не переключаем — у него legacy-привязки к
useRegistrationStore + полям store.walletAgreement/etc. в state. B2
переключения Registrator на новые widget'ы — отдельной story, когда
потребуется почистить legacy.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 15:59:25 +00:00
coopops a967311d1e Revert "feat(controller/onboarding): L3-гейт capital (Эпик 3.1) — AgreementSignaturePort"
This reverts commit 7d90d3af2d.
2026-05-12 14:28:32 +00:00
coopops c7db7a9c6f Revert "feat(desktop/onboarding): SDK selector + Vue OfferGate (Эпик 2.2)"
This reverts commit 3db9854a76.
2026-05-12 14:28:32 +00:00
coopops 3db9854a76 feat(desktop/onboarding): SDK selector + Vue OfferGate (Эпик 2.2)
SDK (Zeus regen из обновлённой schema.gql после Эпика 2.1):
- registrationAgreementSelector — все 10 полей RegistrationAgreement
- Queries.Agreements.GetRegistrationAgreements — query с
  filter coopname/account_type/program_key
- Zeus index.ts / const.ts регенерированы (controller + sdk)

Desktop (FSD feature в components/desktop/src/features/OfferGate):
- useOfferGate composable — реактивно проверяет on-chain agreements
  пайщика через Queries.Agreements.Agreements; signed ↔ существует
  запись (coopname, username, type) со status !== DECLINED
- <OfferGate> Vue компонент c props {coopname, username,
  agreementType, offerTitle, signupUrl?} — рендерит slot если оферта
  подписана, иначе q-banner с кнопкой «Перейти к подписанию»
- model/types.ts — типизация props

Симметричен бэкендовому AgreementSignaturePort (Эпик 3.1): один
вердикт без расхождения между UI и сервером.

pnpm typecheck desktop — exit 0. Контракт-тесты controller/sdk —
тоже зелёные (53). План C28-10 раздел 2.2.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 14:10:39 +00:00
coopops c970d879bc refactor(controller/onboarding): консолидация TTL онбординга (Эпик 4.2)
- Новый модуль domain/onboarding/constants/onboarding-ttl.ts —
  единый источник правды для ONBOARDING_EXPIRY_DAYS (30),
  ONBOARDING_EXPIRY_MS и helper computeOnboardingExpiresAt(startedAt)
- chairman-extension.module и capital onboarding.service используют
  helper вместо дублированного хардкода `30 * 24 * 60 * 60 * 1000`
- Юнит-тест (4 кейса) фиксирует константы и эквивалентность helper'а
  старому inline-вычислению

Runtime-смок: coopback hot-reload зелёный.

53 unit-тестов зелёные. tsc --noEmit exit 0. План C28-10 раздел 4.2.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 14:00:43 +00:00
coopops 7d90d3af2d feat(controller/onboarding): L3-гейт capital (Эпик 3.1) — AgreementSignaturePort
- Новый платформенный порт AgreementSignaturePort + AGREEMENT_SIGNATURE_PORT
  в domain/agreement/ports — расширения проверяют подпись соответствующей
  оферты перед допуском к своим операциям
- AgreementService.hasSigned реализация порта через AGREEMENT_REPOSITORY
  (Postgres backfill on-chain agreements3); подписано ↔ найдена запись
  (coopname, username, type) в любом статусе кроме DECLINED
- @Global() на AgreementModule + useExisting биндинг AgreementService
  на порт; расширения могут инжектить порт без явного импорта модуля
- L3-гейт в InvestsManagementService:
    • createProjectInvest → проверка подписи 'generator' иначе
      ForbiddenException с понятным сообщением для UI;
    • createProgramInvest → проверка подписи 'blagorost' аналогично;
  Используются константы из extensions/capital/constants/capital-agreement-ids.ts
- Юнит-тесты L3-гейта (5 кейсов): отсутствие подписи блокирует обе
  программы, наличие подписи передаёт управление интерактору, подпись
  другого пайщика не открывает доступ (cross-user isolation)

Runtime-смок: coopback hot-reload зелёный (13:53:58), DI порта
зарегистрировано без UnknownDependencies.

49 unit-тестов зелёные. tsc --noEmit exit 0. План C28-10 раздел 3.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 13:55:57 +00:00
coopops 117c0c7c06 feat(controller/onboarding): AgreementQueryPort + GraphQL getRegistrationAgreements (Эпик 2.1)
- Новый платформенный порт чтения соглашений и программ
  (AgreementQueryPort, AGREEMENT_QUERY_PORT) в
  domain/registration/ports — резолверы и расширения инжектят его
  вместо AgreementConfigurationService напрямую, чтобы граница чтения
  оставалась стабильной при будущей перестройке реализации
- useExisting AgreementConfigurationService → AGREEMENT_QUERY_PORT
  биндинг в registration-domain.module
- RegistrationAgreementDTO для GraphQL — спецификация оферты
  (не подписанное Agreement), сливает платформенные + extension-
  зарегистрированные в едином формате
- Новый GraphQL Query getRegistrationAgreements(coopname, account_type,
  program_key?): [RegistrationAgreement!]! — в RegistrationResolver
- RegistrationService.getRegistrationAgreements делегирует порту
- Контрактный тест AGREEMENT_QUERY_PORT (5 кейсов): structural
  implementation check, 4 платформенные оферты для individual,
  пустые программы при пустом реестре, getAgreementById для
  существующей и несуществующей оферты
- Auto-regenerated components/controller/schema.gql

Runtime-смок: GraphQL introspect RegistrationAgreement даёт 10 полей,
живой query getRegistrationAgreements(voskhod, individual) возвращает
4 платформенные оферты с корректным order/applicable_account_types.

44 unit-тестов зелёные. tsc --noEmit exit 0. План C28-10 раздел 2.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 13:47:55 +00:00
coopops 71b20e382d feat(controller/onboarding): платформенный паттерн трёхуровневого онбординга (Эпики 1.1-1.3)
Эпик 1.1 — платформенная инфраструктура реестра:
- AgreementRegistrationSpec / ProgramRegistrationSpec DTO
- AgreementRegistrationPort интерфейс + AGREEMENT_REGISTRATION_PORT токен
- AgreementRegistryService с in-memory state, идемпотентностью по
  (id, extension_name), ConflictException на конфликт владельца,
  tear-down через подписку на EXTENSION_APP_TERMINATE_EVENT
- ONBOARDING_COMPLETED_EVENT + подписка ExtensionLifecycleDomainService
  на восстановление расширения после завершения L1-онбординга

Эпик 1.2 — Capital и Chairman регистрируются через port:
- CapitalPlugin.initialize() → registerCapitalInAgreementRegistry
  при завершённом L1 (5 _done флагов) регистрирует 2 оферты
  (generator/blagorost) и 2 программы (generation/capitalization)
- CapitalOnboardingEventsService.handleDecisionTracked после
  blockchain newresolved эмитит ONBOARDING_COMPLETED_EVENT при
  переходе последнего L1 _done false→true (idempotency через
  wasAlreadyDone guard)
- ChairmanOnboardingEventsService — аналогичный эмит при
  завершении 7 L1 шагов председателя

Эпик 1.3 — чистка ядра controller от capital-специфики:
- AgreementId/AgreementType enum'ы сокращены до 4 платформенных
  (signature/wallet/user/privacy); BLAGOROST_OFFER/GENERATOR_OFFER
  и CAPITAL/GENERATOR удалены
- registration-programs.config.ts удалён (voskhod-hardcode уехал
  в registry capital); registration-agreements.config.ts сокращён
- CooperativeConfigService.getExcludedFromBaseAgreements удалён
- IAgreementConfigItem/IRegistrationProgram типы id/agreement_type/
  key/agreement_ids ослаблены до string — ядро не знает значений
  расширений
- AgreementConfigurationService переписан: inject AgreementRegistryService,
  слияние платформенных оферт с extension-зарегистрированными;
  программы читаются только из registry
- system.service.getRegistrationConfig: requires_selection
  вычисляется как programs.length > 1
- participant.interactor.mapAgreementIdToDocumentType: case'ы
  capital удалены, identity-fallback по Object.values(DocumentType)
- Capital: новый файл constants/capital-agreement-ids.ts —
  локальный source-of-truth для строковых значений оферт/типов/
  программ; используется в register-capital-in-agreement-registry

Тесты: 39 unit-тестов в 5 suites (agreement-registry, capital
plugin-register, capital onboarding-events, chairman onboarding-events,
existing access-policy-union) — все зелёные.

Остаётся как техдолг (не входит в 1.x): DocumentType.BLAGOROST_OFFER/
GENERATOR_OFFER (физические колонки таблицы candidates), ProgramKey
enum в ядре (используется в blockchain payload и switch case
registration-documents.service).

План C28-10, ветка onboarding.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 13:13:00 +00:00
Alex Ant 3561888781 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-12 11:14:51 +05:00
coopops 2e3410b830 fix(ledger2/walletop): убрать O(N) sweep инварианта Σ L3 == L2 из hot path
Полная сверка Σ L3 == L2 через линейный проход secondary-индекса bywallet
выполнялась на каждом walletop для обеих сторон USER_SHARED-кошельков
(стоимость O(N_users) на кошелёк × 2 стороны). На coop'ах с сотнями
пайщиков это даёт квадратичный рост CPU billing на пользовательских
транзакциях, а на тестнете дополнительно блокирует tx из-за исторических
расхождений после миграций 048/049.

Инвариант сохраняется по построению: walletop применяет одно и то же
amount к L2 и L3, а sender-guard (walletop.cpp:46-47) запрещает обход.
Полную сверку выносим на бэкенд («стол бухгалтера») вне hot path.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-12 06:03:00 +00:00
Alex Ant de0f6c7956 chore(release): publish 2026-05-12 09:54:19 +05:00
Alex Ant 5f41b74023 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-12 09:53:57 +05:00
coopops c5eeef124c feat(capital/wallet/V2.3.1): подписи Благороста через regcontrib + backfill orphan'ов
- capital::regcontrib больше не делает dual-write openprogwall для
  program_id=3/4 — остаётся только inline wallet::signagree (документы
  попадают в источник правды wallet::users.programs[]).
- wallet::migrate3 принимает coopname@active помимо wallet@active —
  чтобы контроллер кооператива мог сам бэкфиллить из своей БД.
- V2.3.1 миграция: достаёт реальные подписанные документы Благороста и
  Генератора из blockchain_actions локального controller-PG (audit trail
  capital::regcontrib actions), пушит wallet::migrate3 с реальным
  doc_hash и signed_at для каждого orphan'а в program_id=3/4.
- migrationManager: прокинул VaultDomainService в Migration interface
  (для blockchain.initialize(coopname, wif) перед transact).

Контракты задеплоены на testnet:
  capital  22a882d25395b29692e85bdd10860469341f7783d51538ea96c9685748cd31ab
  wallet   53a12723d77a2a7786044908c44bb6f0117cfc4225009b1f4d532ab5f59fa92a
2026-05-12 04:22:27 +00:00
Alex Ant e270b95996 chore(release): publish 2026-05-11 23:26:00 +05:00
Alex Ant 8d8b01f148 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-11 23:25:41 +05:00
coopops c5922f672f feat(controller/V2.3.0): backfill agreements из soviet::agreements3 в Postgres
На дев/тест-кооперативах controller стартовал со снапшота, старые подписи
(status='') до момента запуска sync не пришли через delta-stream — фронт
требует подписать user/signature/privacy заново, хотя они подписаны на цепи.

Миграция читает agreements3 целиком по scope=COOPNAME через RPC и UPSERT'ит
каждую запись по id. Программные (program_id > 0) пропускает — они идут на
чтение через wallet::users.programs[]. domain-status не трогаем.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 18:25:32 +00:00
Alex Ant bb1d8558e7 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-11 23:11:03 +05:00
coopops e5151758fb fix(migrator/049): blocked может быть undefined (binary_extension) — подменять нулём
soviet::progwallets имеет blocked и membership_contribution как
binary_extension. На старых записях (например voskhod/enzqwnqsdqar/1)
eosjs возвращает undefined — pushAsset падает с
"Expected string containing asset". Защищаемся ?? zeroAssetLike(pw.available).
Для membership ?? уже был.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 18:10:42 +00:00
Alex Ant a575da57f8 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-11 23:08:28 +05:00
coopops 9352c77cd7 feat(migrate3): подписывать миграционные actions самим контрактом, не coopname
У нас нет приватных ключей от кооперативов, которых мы мигрируем.
Поэтому ledger2::migrate3 и wallet::migrate3 теперь принимают auth от
get_self() (т.е. ledger2@active / wallet@active), и они же платят за RAM.
Mig-скрипты 047/048/049 пушат actions с актором = имя контракта.

Также правки в ledger2::migrate (Эпик 1) с прошлой сессии: default-case
для неизвестных legacy account IDs (862-867) — `break;` вместо
eosio_assert (ignore non-canonical), плюс IS_TESTNET-блок с clamp'ом
грязных legacy-данных.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 18:07:17 +00:00
Alex Ant add7646720 chore(release): publish 2026-05-11 15:38:44 +05:00
Alex Ant 0d8006d981 chore(release): publish 2026-05-11 12:02:00 +05:00
Alex Ant f9d253117c Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-11 12:01:42 +05:00
coopops c6b144661f [@ant] fix(ledger2/migrate): test-build толерантен к грязным legacy-остаткам
На IS_TESTNET=1 сборке вместо abort'а clamp'им:
- entry > cash → entry = cash, share_money = 0;
- РИД-часть на legacy 80 → игнорируется (лишний остаток теряется);
- Σ p.minimum_amount > share → clamp Σmin = share, share_remain = 0.

В prod (без IS_TESTNET) три инварианта остаются строгими: миграция падает
с прежним явным сообщением, оператор разбирается ad-hoc.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 07:01:12 +00:00
Alex Ant a55005a212 chore(release): publish 2026-05-11 11:28:06 +05:00
Alex Ant 5ae6f4963d Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-11 11:27:49 +05:00
coopops f64e028709 [@ant] fix(ledger2/migrate): игнорировать legacy acc id вне канона (51/80/861)
Группа 862..867 (RESERVE/INDIVISIBLE/ECONOMIC/MUTUAL/DEVELOPMENT/DELEGATE_FEES)
в ledger2 отдельными кошельками не выделена. Падать на ненулевом 867
(найдено на testnet) — блокирует миграцию; вместо этого пропускаем.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 06:27:31 +00:00
coopops 33f44dc823 [@ant] fix(migrator/047): мигрировать program-соглашения с пустым статусом
Фильтр `status === 'confirmed'` пропускал всё: после Эпика 2 для program_id > 0
sndagreement пишет ""_n, а confirmagree больше не вызывается (воркфлоу ушёл
в wallet::signagree). Заменено на `status !== 'declined'`; wallet::migrate3
идемпотентен.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 05:46:45 +00:00
Alex Ant dd88047d76 chore(release): publish 2026-05-11 09:57:46 +05:00
Alex Ant b9d06e4e68 Merge pull request #357 from coopenomics/reports
[989] платформа ФНС/ФСС отчетов и еще 1000 фиксов
2026-05-11 09:56:58 +05:00
coopops 8e263b7424 Merge remote-tracking branch 'origin/reports' into reports 2026-05-11 04:52:50 +00:00
coopops 876d06046b Merge remote-tracking branch 'origin/dev' into reports
# Conflicts:
#	components/contracts/cpp/soviet/src/wallet/addbal.cpp
2026-05-11 04:51:43 +00:00
coopops c5e23f15f9 [@ant] feat(ledger2/capital/voskhod): preimp-учёт + voskhod L2/L3 хардкод-миграция
- ledger2 wallets +`w.cap.preimp` (USER_SHARED, 5 пайщиков-преимп) и `w.sov.expns`
  (COOPERATIVE, хоз.расходы из числа целевого финансирования). Реестр 11→13.
- operations: `o.cap.import` и `o.cap.actprp` Dr 51→**Dr 04** (РИД-имущество, не
  деньги). Новые `o.cap.preimp` (ISSUE Dr 04/Cr 80) и `o.cap.drppre` (BURN Dr 80/
  Cr 04 — закрытие пред-импорт-учёта при переходе на электронный учёт).
- processes: +`p.cap.preimp` (одноактовый).
- migrate_voskhod_facts полностью переписан: вместо send_transit-apply'ев —
  прямой emplace `accounts2` (51=176 800, 04=62 353 311, 08=543 400, 80=
  62 946 011, 86=127 500; Σ Dr=Σ Cr=63 073 511) + прямой emplace `wallets2`
  (5 кошельков) + L3 для 5 преимп-пайщиков с `participants.find()`-guard'ом
  (тестнет-safe). L3 для остальных USER_SHARED-кошельков заводят migrator-048/049.
- capital::importcontrib: перед `o.cap.import` проверяем `userwallets[w.cap.preimp,
  username]` и при наличии вызываем `o.cap.drppre` на полный preimp.available
  (один process_hash на цепочку IMPORT).
- cooptypes mirror (operations.ts/processes.ts) + generated wallets из C++.
- controller process-hash-locator: +`p.cap.preimp` (entity-таблицы пока нет,
  process_hash берётся из blockchain_actions).

Терминология: «до перехода на электронный учёт» (договор УХД с 5 пайщиками
voskhod подписан был задолго до миграции; они не успели в электронный учёт).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-10 16:27:00 +00:00
Alex Ant 996012399e chore(release): publish 2026-05-10 14:39:10 +05:00
Alex Ant c4ffdae7ef chore(release): publish 2026-05-10 14:36:47 +05:00
Alex Ant e60d339d2b Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-10 14:36:25 +05:00
coopops e7241d8a91 [@ant] feat(soviet/setminamt): action для правки minimum_amount у пайщика
Технический фикс: для уже-accepted пайщиков нет публичного action для
коррекции minimum_amount, апдейт делался только через addpartcpnt (создание)
и unblock (восстановление). Когда поле рассинхронизировано с кооп-минимумом
(как у voskhod::ant — 1 RUB вместо 300 RUB), править нечем.

Action setminamt(coopname, username, minimum):
  require_auth(coopname); проверяет символ; modify только minimum_amount.

Why: блокирует чистый расчёт Σ minimum_amount при миграции voskhod→ledger2.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-10 09:33:04 +00:00
coopops 64c11820b0 [@ant] refactor(soviet/converttoaxn): убрать legacy-зеркало soviet.programs/progwallets
Удалён `Wallet::sub_available_funds(_soviet, _provider, ...)` — единственный
канал, через который converttoaxn ещё двигал legacy soviet::progwallets и
counter в soviet::programs (pid=1). Теперь весь учёт идёт только через
ledger2::apply CONVERT_AXN (TRANSFER SHARE_FUND_PAY → DELEGATE_FEES,
Dr 80 / Cr 86), который уже стоял рядом.

Why: converttoaxn — действие только voskhod (у других коопов нет AXN);
включается одновременно с его миграцией в ledger2, поэтому legacy-зеркало
больше не нужно.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-10 08:16:08 +00:00
Alex Ant bfe5592ae9 chore(release): publish 2026-05-10 12:01:35 +05:00
Alex Ant 9e94510981 chore(release): publish 2026-05-10 12:01:08 +05:00
Alex Ant b432ad155d Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-10 12:00:19 +05:00
coopops eea5652d1f [@ant] fix(soviet/addbal): upsert progwallets — создавать кошелёк если отсутствует
Раньше addbal падал с "Кошелёк не найден" для пайщика без progwallets-записи
по программе. Теперь, если записи нет — создаём её с нулевыми blocked/membership
и сразу зачисляем quantity в available. Если есть — прежняя логика available += quantity.

Why: на mainnet voskhod у части пайщиков нет progwallet pid=1, и ручные начисления
паевого взноса по УХД через addbal падали ассертом.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-10 06:59:36 +00:00
coopops 31da96dceb [598-3][@ant] chore(standards): удалить устаревший p.mkt.reqst.standard.yaml
Стандарт описывал клиринговую модель donor'а (паевый взнос имуществом
+ возврат паевого взноса имуществом). На ветке marketplace2 заменён
тремя новыми стандартами под членскую модель Стол заказов MVP:
  • p.mkt.supply.standard.yaml   — Прямая поставка-приобретение имущества
  • p.mkt.return.standard.yaml   — Гарантийный возврат имущества
  • p.mkt.wroff.standard.yaml    — Утилизация скоропорта

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-10 06:08:07 +00:00
Alex Ant 57cb8f4302 Merge pull request #364 from coopenomics/ledger3
ledger3 → reports: Эпики 2-3 + фиксы соглашений и L3-миграции
2026-05-10 11:05:59 +05:00
coopops bb9db28e99 [@ant] feat(capital): валидация startproject — мастер + active-родитель + UX-док
Контракт capital::startproject:
- проверка project.master != ''  (без мастера коммиты некому одобрять)
- для компонента (parent_hash != 0): родитель должен быть в статусе active
  (иначе компонент окажется в работе под закрытым/незапущенным проектом)

Реестр операций (human_name → пользовательский язык):
- o.cap.cnvshr: «РИД → паевой взнос деньгами» → «РИД → главный кошелёк»
  (operations.hpp + cooptypes/operations.ts + p.cap.rid.standard.yaml)

Документация:
- docs/new/blagorost/lifecycle.md — пользовательская доп-инфо в таблице
  статусов и в «Что важно помнить»: запуск Компонента возможен только при
  назначенном мастере и активном Проекте.
- docs-harness/scenarios/blagorost/{commits-master,master-and-plan}.mjs —
  пометка для автора сценариев о пред-условиях запуска компонента.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-10 06:03:58 +00:00
coopops f5ddddbd67 [@ant] refactor(capital+ledger2): convertsegm = финальная фаза p.cap.rid, единый result_hash
Раньше конвертация сегмента (`convertsegm`) была отдельным процессом
`p.cap.cnvseg` со своим `convert_hash` — но фактически это завершающая
фаза внесения РИД, а не самостоятельный процесс. Объединяем под
`p.cap.rid` с единым анкером `result_hash` от pushrslt до convertsegm.

Контракт capital:
- convertsegm.cpp перенесён convert_segment/ → push_result/, payload и
  memo получают result_hash вместо convert_hash; перед apply проверяет
  result.status == ACT2 + project_hash/username match.
- signact2 НЕ удаляет result — переводит в ACT2 (анкер до convertsegm),
  delete_result переехал в convertsegm.
- segment-conversion-process.dox смержен в result-submission-process.dox
  (новый шаг 8 + диаграмма + эффекты/документы).

ledger2:
- processes::capital::CNVSEG удалён, RID комментарий расширен.
- o.cap.cnvshr/o.cap.cnvbl: process_type → p.cap.rid.

cooptypes / SDK / controller:
- IConvertsegm.convert_hash → result_hash, regen + snapshot обновлён.
- DTO/domain/mutation-log: convert_hash → result_hash.
- PROCESS_HASH_LOCATOR: убран p.cap.cnvseg, p.cap.rid комментарий
  расширен (4 операции + анкер result_hash).
- schema.gql + zeus regenerated.

Desktop:
- ConvertSegment: result_hash берётся из resultStore по
  (username, project_hash), а не генерируется случайным.

Стандарт p.cap.rid:
- convertsegm как closer, новое state `converted` (final), transition
  accepted → converted, scenario step 8, документ заявления конвертации
  (registry_id TBD-Standardization), operations o.cap.cnvshr/cnvbl.
- o.cap.accept переведён на wallet_op NONE (без TRANSFER кошелька).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-09 14:29:22 +00:00
coopops d838c61ddd [@ant] fix(controller): добавить в PROCESS_HASH_LOCATOR p.cap.wthcap и p.cap.cnvseg
Без этих ключей integrity-check на старте падал, контроллер крашился:
'p.cap.wthcap, p.cap.cnvseg' пришли в OPERATION_CODE_TO_PROCESS_TYPE из
cooptypes (WITHDRAW_FROM_CAPITAL, CONVERT_TO_SHARE/CONVERT_TO_BLAGO).

- p.cap.wthcap → capital::prgwithdraws.withdraw_hash (жизнь запроса).
- p.cap.cnvseg → [] (одноактовый convertsegm; данные из blockchain_actions).
2026-05-09 13:11:13 +00:00
coopops 5c2d54707c [@ant] fix(controller): user_wallets partial unique-index — depo после auto-cleanup в чейне больше не валится duplicate-key
Контракт ledger2 удаляет L3-запись при обнулении (cleanup_l3_if_empty) и при
следующей операции на той же паре (wallet_name, username) выдаёт новый id.
Postgres-mirror хранит удалённые записи с present=false для версионирования —
полный unique idx_user_wallets_natural_key блокировал upsert новой row,
дельта депозита проваливалась с duplicate key, баланс в UI замирал.

- entity: @Index ... { unique: true, where: '"present" = true' }
- UserWalletIndexInitializer (OnModuleInit): пересоздаёт индекс как partial,
  потому что TypeORM synchronize не сравнивает WHERE и держит обычный unique
2026-05-09 13:06:22 +00:00
coopops 2acc233897 [@ant] fix(capital): createpinv обновляет геймификацию (energy/level) у программного инвестора
Прямая инвестиция в Благорост не имеет сегмента, поэтому считаем energy_gain
от amount напрямую и вызываем add_energy_and_check_levelup. До патча уровень
не рос при createpinv — только при createinvest (через update_gamification_from_segment).
2026-05-09 12:50:23 +00:00
coopops 2c0c2a9e40 [@ant] fix(ledger2): human_name w.wal.share «ЦК — паевая часть пайщика» → «Паевой взнос пайщика» 2026-05-09 12:29:48 +00:00
coopops e474f6ae12 [@ant] fix(desktop): реестр кошельков — обернуть id в WalletIdCell для единообразия с проводками/счетами 2026-05-09 12:27:29 +00:00
coopops a745e798a4 [@ant] fix(controller+capital): event-driven regshare + delete-row aware реестр кошельков
- controller: listener delta::ledger2::userwallets[w.cap.blago] синхронизирует regshare без ожидания scheduler-тика 1440 мин
- typeorm-ledger2-state.repository: getWallets/getAccounts берут самую свежую row на ключ и при present=false обнуляют суммы (не выкидывают), чтобы удалённый L2-кошелёк остался раскрываемым в реестре с историей
- capital: inline regshare после apprvappndx + whitelist auth в regshare
- programs.hpp: is_participant_of_cpp_by_program_id через wallet::users.programs[], get_program_wallet → has_program_wallet
- cooptypes/operations: human_name «Коммит РИД по программе Генератор», убрано «(перенос между кошельками)»
2026-05-09 12:12:10 +00:00
coopops 88b285448a chore(boot): убрать opensearch из reboot.sh
OpenSearch требователен по ресурсам и подвешивает локалку;
нужен редко — поднимаем вручную при необходимости.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-09 11:01:22 +00:00
coopops e77a1268db feat(ledger2): WalletOp::NONE — внутрибалансовые проводки без движения кошелька
ACCEPT_RID теперь оставляет кошелёк на w.cap.gen и пишет только Dr 04 / Cr 08;
кошельковое перемещение (на ЦК или Благорост) делается отдельным шагом
convertsegm. CONVERT_TO_SHARE/CONVERT_TO_BLAGO — TRANSFER без бухпроводок,
так как двойная проводка уже была сделана при ACCEPT_RID.

apply.cpp пропускает walletop при NONE; walletop.cpp режет op_code=5 на входе.
Static_assert none_pattern_correct() гарантирует пустые wallet_from/to и
обязательные debit/credit.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 18:40:38 +00:00
coopops f051196754 feat(apps): pricing validation + clients table + D4 regsub extension (stories v2.1.2, v2.4.1, v2.5.0)
Батчем все контрактные сторы эпиков v2.1/v2.4 + implicit D4-расширение
из эпика v2.5, чтобы CA-сторона могла строить write-port'а против
финальных on-chain сигнатур, не возвращаясь в Mono.

Story v2.1.2 — setpricing валидация:
  - hourly_rate.amount > 0 (eosio_assert)
  - package_id и plan непустые
  - snapshot policy: НЕ трогаем subs (оплаченные периоды не пересчитываются
    при смене тарифа), audit-snapshot — off-chain (journal-less invariant)

Story v2.4.1 — clients table (D3) + regclient/delclient:
  - scope = catalog_operator, PK = client_coopname
  - regclient: строгий insert (eosio_assert на дубль), RAM payer = operator
  - delclient: erase с eosio_assert на отсутствие
  - в MVP всегда voskhod-as-operator, но scope-based не блокирует replica

Story v2.5.0 (implicit, D4) — regsub extension + idempotent extend:
  - sub.attempt: uint8 = 0 — billing-retry counter
  - sub.last_charge_intent_id: checksum256 = 0 — UUIDv5 последнего charge
  - extendsub(operator, subscriber, package_id, period_seconds, intent_id):
    идемпотентный extend, eosio_assert("already extended") при дубле intent_id;
    end_at += period_seconds, attempt → 0, обновляет updated_at
  - setattempt(operator, subscriber, package_id, attempt) — для retry-watcher
  - migration safe (subs пустая в dev/MVP; pre-deploy guard
    scripts/v2-migration-guard.ts блокирует прод при count > 0)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 17:04:43 +00:00
coopops 46d1d49fae [@ant] refactor(contracts+desktop): срез двойного учёта progwallets — переход на ledger2 как источник правды
capital/balances: get_capital_program_*_share_balance читают L2/L3 ledger2
(wallets[BLAGOROST_FUND] и userwallets[(w.cap.blago, username)]) вместо
soviet::progwallets — фикс «Благорост = 0% после pushresult».

phase A: удалены прямые Wallet::add/sub/block/unblock_funds в 10 callers
(capital: signact2, act2pgprp, createinvest, createpinv, capauthwthd3,
importcontr; wallet: completewthd, completedpst, createwthd, declinewthd) —
во всех есть зеркальный Ledger2::apply, дубль создавал параллельный учёт
в legacy progwallets и разъезжался с L3 при первом же сбое.

phase B: convertsegm.cpp переписан на 2 × Ledger2::apply. В реестр операций
добавлены o.cap.cnvshr (TRANSFER GENERATOR_FUND→SHARE_FUND_PAY, Dr 80/Cr 08)
и o.cap.cnvbl (TRANSFER GENERATOR_FUND→BLAGOROST_FUND, Dr 04/Cr 08) +
новый процесс p.cap.cnvseg для аудит-следа отдельно от ACCEPT_RID.

desktop/WalletProgramWidget: блок «Заблокировано» рендерится только при
parseFloat(blocked) > 0; убран хак с подмешиванием minimum_amount к ЦК.

Marketplace вынесен в отдельный заход.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 17:02:41 +00:00
coopops 1c573bf131 feat(apps): on-chain skeleton — таблицы pricings/globals и actions setpricing/setglobals (story v2.1.1)
Каркас для v2 каталога приложений: scope-per-package таблица `pricings`
(D1) + singleton `globals` (D2) + два action'а с `require_auth(get_self())`
без бизнес-валидации. Unblock'ает CA-команду для написания TS write-port'а
против стабильных on-chain сигнатур; полная валидация и snapshot policy
выезжают в story v2.1.2.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 16:41:19 +00:00
coopops 9a5d41d03c [@ant] fix(desktop): отложить loadUserWallet после инвеста на 4с — нет «мерцания»
Сразу после chain-мутации parser2 → consumer → PG отстаёт на 1-3с, и
немедленный loadUserWallet возвращает ещё стейт до инвеста; внутри он
clearOptimisticPatches() — оптимистичный патч стирается, UI откатывается
к до-инвеста. Через ~3-5с какой-то фоновый refetch получает уже свежие
данные и UI снова прыгает на новое значение.

Откладываем рефетч на 4с (не await — fire-and-forget). За это время
дельта прилетает, refetch получает уже-после-инвеста, патч чисто
сменяется серверной правдой без промежуточного отката.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 14:39:27 +00:00
coopops 440e46436d [@ant] fix(desktop): program_type через Zeus.ProgramType (UPPER_CASE из GraphQL), debug-логи убраны
Корень: GraphQL сериализует enum ключами (MAIN, BLAGOROST), не значениями.
Использую типизированный Zeus.ProgramType.MAIN / .BLAGOROST вместо
хардкода строк — единый источник, не разъедется со схемой.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 14:34:37 +00:00
coopops ad20c714b1 [@ant] debug(desktop): MicroWallet — console.log program_wallets когда ЦК не найден
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 14:32:17 +00:00
coopops 51175f8d2f [@ant] fix(desktop): program_type для ЦК = 'main' (controller-enum), не 'wallet'
controller/src/domain/wallet/enums/program-type.enum.ts маппит program_id=1
на ProgramType.MAIN ('main'), а не 'wallet' — это другой источник, чем
cooptypes/src/ledger2/programs.ts.internal_name. UI читает поле program_type
с бэкенда, поэтому фильтр и optimistic-патч должны использовать 'main'.

Без этого MicroWallet.find(program_type==='wallet') возвращал undefined
(в углу 0 вместо ЦК-баланса), а optimistic-патч на ЦК молча промахивался.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 14:26:14 +00:00
coopops 2913757f7b [@ant] fix(desktop): MicroWallet ищет ЦК по program_type, optimistic-патч инвеста зачисляет в Благорост (available)
- MicroWallet: вместо program_wallets[0] — find(program_type === 'wallet').
  Порядок program_wallets от backend недетерминирован, в углу мог оказаться
  Благорост / Генератор вместо ЦК.
- CreateProgramInvest: optimistic-патч на стороне Благорост был
  program_type='capital' + blocked_delta — мисматч (internal_name='blagorost')
  и не та полка (UI читает available из L3 ledger2::userwallets, поскольку
  Ledger2::apply(INVEST) делает TRANSFER в .available; progwallets.blocked
  десктоп не отображает). Поправлено на 'blagorost' + available_delta.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 14:15:42 +00:00
coopops c8616deb76 [@ant] feat: regcontrib через wallet::users, optimistic-overlay кошелька, sync статуса пайщика
Контракты:
- wallet::signagree: auth = coopname OR contracts_whitelist; payer = подавший
  auth (RAM-аккаунтинг). Снимает auth-блок при inline-вызове из capital.
- capital::regcontrib: gate Благорост-соглашения через wallet::users.programs[]
  (ADR-008) вместо legacy progwallets; inline signagree от _capital@active —
  атомарная связка payload → wallet::users → реестр.
- ledger2::migrate: compute_min_total_by_type через participant.minimum_amount
  (фактический зафиксированный взнос пайщика), а не coop.minimum (мог быть
  повышен после вступления — приводило к Σ L3 > L2 на w.reg.minshr). Убрано
  неявное clamping → явный eosio::check + понятная ошибка.
- wallet::createwthd/declinewthd, capital::createpinv/createinvest/capauthwthd3:
  Ledger2::apply на USER_SHARED-кошельках (REQUEST_WITHDRAW, DECLINE_WITHDRAW,
  INVEST, WITHDRAW_FROM_CAPITAL).
- operations.hpp/processes.hpp: новые записи реестра.

cooptypes: зеркало новых operations/processes (o.cap.wthcap, o.wal.wthreq,
o.wal.wthdec, p.cap.wthcap).

Migrator: 048 пишет L3 по participant.minimum_amount; gate на
ledger2::meta.migrated до запуска (без миграции migrate3 разъезжается с L2).

Controller:
- ParticipantStatusSyncService: action::soviet::addpartcpnt → users.status='active'.
  Без него ActiveUserStatusGuard блокирует свежепринятых пайщиков на
  createDepositPayment и других мутациях — статус так и оставался '4_Registered'.
- migrations/V2.2.0: backfill users.status='active' по soviet::participants
  из chain (через BLOCKCHAIN_RPC).
- registration-programs: «Программа Капитализация» → «Программа Благорост».

Desktop:
- useWalletStore: универсальный optimistic-overlay (applyOptimisticPatch /
  TTL / clearOnLoad). program_wallets — теперь computed поверх raw-стейта;
  серверный refetch перетирает overlay.
- CreateProgramInvest: оптимистично списывает ЦК и зачисляет blocked
  Благороста до подтверждения цепочкой, ревертит при ошибке.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 13:29:11 +00:00
Alex Ant f35a13a382 chore(release): publish 2026-05-08 10:56:03 +05:00
Alex Ant aced4966c8 chore(release): publish 2026-05-08 10:37:35 +05:00
Alex Ant 978d94f6b7 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-08 10:37:06 +05:00
coopops e5613405f4 fix(ci): запинить pnpm через packageManager + allowlist build-скриптов
Без пина CI каждый раз тянул latest pnpm; на 10.4+ ignored builds
из warning стали ERR_PNPM_IGNORED_BUILDS, и `pnpm install --frozen-lockfile`
валился на electron/esbuild/@parcel/watcher и пр.

- packageManager=pnpm@10.33.0 в корневом package.json (синхронно с
  publish-packages.yaml и components/boot/Dockerfile)
- pnpm.onlyBuiltDependencies — 18 пакетов из лога фейла
- Dockerfile: corepack enable вместо `npm install -g pnpm` (обе стадии)
- publish-docs.yaml: pnpm/action-setup@v4 без version + cache: pnpm

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-08 05:35:36 +00:00
coopops a6b9352a18 [@ant] fix(soviet): addbal — upsert progwallets вместо «Кошелёк не найден»
Депозит-флоу wallet::completedpst → Wallet::add_available_funds →
soviet::addbal падал с «Кошелёк не найден», если у пайщика ещё не было
строки в soviet::progwallets для программы. Подписание соглашения
(wallet::signagree) progwallets-запись не открывает по дизайну (ADR-008,
state источника правды — wallet::users.programs[]).

addbal теперь делает upsert: если записи нет — создаёт с нулевыми
балансами и сразу прибавляет quantity. Если есть — стандартный modify.
agreement_id=0 (соглашения для legacy progwallets уже не нужны:
актуальная подпись лежит в wallet::users).

Subbal/blockbal/unblockbal/addmemberfee оставлены как есть — для них
запись должна существовать (нечего блокировать/списывать с пустого).
2026-05-07 17:10:52 +00:00
Alex Ant b41a42ad0a chore(release): publish 2026-05-07 22:09:20 +05:00
Alex Ant 16ee154424 chore(release): publish 2026-05-07 22:09:01 +05:00
Alex Ant a15432233e Merge branch 'testnet' of github.com:coopenomics/mono into testnet 2026-05-07 22:08:48 +05:00
Alex Ant ba96a650b8 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-07 22:08:01 +05:00
coopops 4011628e2a Merge branch 'dev' into testnet 2026-05-07 16:53:40 +00:00
coopops 1f9753cf8d [@ant] fix(capital/permissions): UNION-роли — соавтор-член-совета может править артефакты
Регрессия: getProjectUserRole коротко замыкался на BOARD_MEMBER при userRole='member' и не доходил до segment.is_author. В матрице BOARD_MEMBER.EDIT_REQUIREMENT=false → permissions.can_edit_requirement=false → редактор открывался read-only у соавтора, который одновременно член совета.

Фикс — UNION-семантика: пользователь может одновременно нести несколько ролей (member + author + master + …), итоговое право — OR по матрицам всех его ролей. Симметрично для issue-уровня (submaster + author и т.п.). Чистые роли работают как раньше.

12 unit-тестов на ключевые комбинации (BOARD_MEMBER+AUTHOR, CHAIRMAN+MASTER, переходы статусов).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-07 16:52:30 +00:00
coopops d11282bc98 [@ant] feat(controller): «Стол бухгалтера» в реестре расширений
Манифест reports-расширения (controller/extensions.registry) — title и
title desktops с «Отчёты ФНС» на «Стол бухгалтера». Description
расширил под фактическое наполнение: реестры операций / проводок /
кошельков / счетов плюс налоговые формы.
2026-05-06 19:41:26 +00:00
coopops df6a724a03 [@ant] feat(reports): «Стол бухгалтера» + читаемые Активный/Пассивный и Дебет/Кредит
* Расширение переименовано с «Отчёты ФНС» на «Стол бухгалтера» (заголовок
  и breadcrumb).
* AccountsPage: Активный/Пассивный (тип счёта) и Дебет/Кредит (сторона
  проводки) теперь theme-aware — светлая тема blue-grey-9 / brown-8,
  тёмная blue-grey-3 / brown-3, weight bold. Старый text-blue-grey-8 /
  text-brown-7 на тёмной теме читался плохо.
2026-05-06 19:32:28 +00:00
coopops 03351c10c2 [@ant] fix(desktop): автозагрузка inline-children при cross-link на операцию
OperationsPage в onMounted, при ?operation_id=…, разворачивал строку через
expanded.set, но не дёргал loadChildOps — поэтому таблицы «Движения по
кошелькам» и «Проводки по счетам» оставались пустыми до ручного
схлопывания/раскрытия. Теперь после load() сразу подгружаем сибсов
найденного apply'а по его processHash.
2026-05-06 19:21:20 +00:00
coopops 2b1bb54e94 [@ant] fix(desktop): убрать TS-ассерт ! из template-выражения PostingsPage
`props.row.debitGlobalSequence!` в pug-атрибуте @click парсился как
постфиксный `!` (Quasar boot error: missing ) after argument list).
Заменил на `String(props.row.debitGlobalSequence)` — `v-if` гарантирует
non-null, но компилятору шаблона нужен валидный JS.
2026-05-06 19:11:08 +00:00
coopops 50e6e9daae [@ant] refactor(ledger2): пары debit/credit и parent apply через creator_action_ordinal
Связь apply-orchestrator ↔ inline walletop/debit/credit строится точечно через
явные идентификаторы parser2: пара `(transaction_id, creator_action_ordinal)`
inline-action указывает на `(transaction_id, action_ordinal)` родителя.

* getPostings: парный credit подтягивается LEFT JOIN на (transaction_id,
  creator_action_ordinal). Удалён эвристический алгоритм
  «closest-credit-after-debit-without-apply-between». Родительский apply
  тоже точечно через (transaction_id, action_ordinal=d.creator_action_ordinal)
  без ограничения по name — ловит и revert как родителя inline-проводок.
* getHistory: parentApplyGlobalSequence в SELECT, applyGlobalSequence /
  parentApplyGlobalSequence фильтры — все через те же точечные JOIN'ы.
  Удалены multi-effect range-эвристики «между этим apply и следующим
  с тем же processHash».
* Фильтр по accountId/walletName: для apply/revert — EXISTS-проверка
  inline ребёнка (debit/credit или walletop) с этим account_id/wallet.
  Прямое сравнение для самих debit/credit/walletop/walmove.
* Удалены мёртвые ветки `data->>'id'` (нет такого поля у ledger2-actions).
* Никаких fallback'ов: parser2 даёт creator_action_ordinal для каждого
  inline нативно — отдельной ветки «если родитель не нашёлся, ищем
  ближайший apply» нет.
2026-05-06 18:54:34 +00:00
coopops 973e70aba5 [@ant] feat(reports): отдельные колонки № проводки/№ процесса через EntityIdBadge
* PostingsPage: «№ проводки» (debit.global_sequence) и «№ процесса»
  (process_hash) — отдельные колонки, оба EntityIdBadge с hover-эффектом и
  копированием по клику. Tooltip про парный credit убран.
* OperationsPage: «№ операции» (apply.global_sequence) и «№ процесса» —
  отдельные колонки EntityIdBadge.
* CoopWalletsPage: «№» движения (walletop.global_sequence) — EntityIdBadge.
* AccountsPage (история проводок счёта): добавлены колонки «№ проводки»
  (debit/credit.global_sequence) и «№ процесса». Cross-link «К операции»
  теперь точечный — через operation_id (apply.global_sequence) вместо
  process_hash, чтобы не открывалось несколько операций.
* Hint у поисковых input'ов убран (мешал стабильному layout).

Backend: добавлен parentApplyGlobalSequence в Ledger2Operation — для
точечного cross-link из debit/credit в реестр операций.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 18:26:49 +00:00
coopops e0d6de216d [@ant] feat(ledger2): уникальные ID операций/проводок/движений в реестрах
Используем существующий blockchain_actions.global_sequence (unique-индекс)
как канонический ID — без изменений контрактов и схемы БД.

* «№ операции» = apply.global_sequence (точечная адресация одного apply
  + его siblings; multi-effect-защита через диапазон до следующего apply
  того же processHash).
* «№ проводки» = debit.global_sequence; парный credit подтянется
  стандартным алгоритмом «closest-credit-after-debit-without-apply-between».
* «№ движения» = walletop.global_sequence.

Backend: новые фильтры applyGlobalSequence/walletopGlobalSequence в
getLedger2History и debitGlobalSequence/applyGlobalSequence в
getLedger2Postings. Frontend: колонки № операции (OperationsPage),
№ проводки (PostingsPage), № движения (CoopWalletsPage). Универсальный
search-input на каждой странице — определяет тип ID по формату ввода
(цифры → seq, hex64 → process_hash).

URL-параметры унифицированы: ?operation_id=apply.global_sequence,
?posting_id=debit.global_sequence, ?process_hash=hex64.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 18:02:55 +00:00
coopops 55617dd814 [@ant] fix(desktop): отчёты — единая стрелка, тёмная тема календаря, поиск убран из проводок
* AccountsPage / CoopWalletsPage: иконки кросс-линков в реестр операций
  (fa-up-right-from-square / fa-list-ul) заменены на fa-arrow-right —
  одинаково с ParticipantWalletsPage и PostingsPage.
* OperationsPage: убран text-grey-10 со столбца «Сумма» — на тёмной теме
  тёмный шрифт сливался с фоном.
* ReportsCalendar / CalendarCell: все hex-цвета через rgba + body--dark
  overrides. Раньше календарь оставался белым на тёмной теме.
* PostingsPage: убран UI-инпут поиска по process_hash + связанные chip /
  filter / handler. Реестр операций — единственная точка поиска (там видно
  и проводки, и движения по кошелькам в одной развёрнутой строке).
  Cross-link account_id / username по query-параметру сохранён.
* WalletTransferDialog: добавлен #no-option слот и hint в q-select
  «В кошелёк». Если у кооператива нет других кошельков на бух.счёте
  источника, пользователь видит причину пустого списка, а не молчаливый
  пустой dropdown.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 17:22:55 +00:00
coopops 26ca889aff [@ant] feat(reports): кнопка «К операции» в реестре проводок
Из строки проводки можно одним кликом провалиться в реестр операций
с фильтром по process_hash и раскрытой нужной apply-операцией. На больших
multi-effect процессах (несколько apply внутри одного process_hash) это
важно: query.operation_id ведёт ровно к parent apply этой проводки, а не
к первой попавшейся.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 17:05:00 +00:00
coopops 00f9e2174b [@ant] chore(reports): убран COALESCE(amount, quantity) — quantity в ledger2-actions не существует
В предыдущем коммите оставил COALESCE «на случай walmove/revert». Проверил
ledger2.hpp — все actions (debit/credit/apply/walletop/walmove/revert) принимают
только amount. Поля quantity в data ledger2 нет ни у кого. Возвращаю один amount.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 16:57:24 +00:00
coopops 040b603cb8 [@ant] fix(reports): реестр проводок — Сумма и Пайщик из debit-action и parent apply
ledger2::debit и ledger2::credit принимают только coopname/account_id/amount/
process_hash/memo (см. ledger2.hpp), поля username у них нет, а сумма лежит
под ключом amount, не quantity. Резолвер getLedger2Postings:
- quantity = COALESCE(d.data->>'amount', d.data->>'quantity') — последний
  на случай legacy walmove/revert, у них quantity;
- username берётся из ближайшего parent apply того же process_hash;
- фильтр по username — тоже через parent apply (subquery).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 16:47:02 +00:00
coopops 5fa303f850 [@ant] feat(reports): реестр проводок — четвёртая страница в Отчётах ФНС
Раньше проводки (Дт/Кт/Сумма) были видны только при разворачивании
отдельной операции в реестре операций. Не было плоской ленты «все
проводки кооператива», для бухгалтерской сверки приходилось разворачивать
каждую операцию вручную.

Бэкенд: новый GraphQL Query getLedger2Postings(input). Резолвер
восстанавливает пары debit+credit из blockchain_actions по правилу
«ближайший parent apply того же process_hash» — multi-effect процесс с
несколькими apply внутри одного process_hash даёт несколько проводок,
каждая закрыта своим apply'ем. Серверные фильтры: accountId (попадание
в Дт ИЛИ Кт), processHash, username, dateFrom/dateTo. Пагинация.

Фронт: страница /reports/postings рядом с операциями/кошельками/счетами.
Колонки: Дата | ID процесса | Операция (chip с цветом по контракту) |
Дебет | Кредит | Сумма | Пайщик. Клик на хэш — копирует. Tooltip на
коде счёта показывает название (через AccountIdCell + getAccountName).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 15:24:04 +00:00
coopops d1bd208ec7 [@ant] feat(reports): календарь — статус before_registration вместо overdue до даты регистрации
При подключении кооператива в середине года все периоды до этой даты
показывались красным «просрочен» — пол-календаря в красном раздражает
и фактически некорректно: эти отчёты сдавать не надо.

Резолвер тянет registrator::accounts(coopname).registered_at и для ячеек
с dueDate < registered_at возвращает новый статус BEFORE_REGISTRATION.
Приоритет: ручные отметки (NOT_REQUIRED / SUBMITTED_EXTERNALLY) перебивают,
если пользователь уже что-то проставил.

Фронт рендерит ячейку нейтрально-серой, без hover-обводки и без клика —
открывать там нечего.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 15:10:36 +00:00
coopops 07d414f761 [@ant] fix(desktop): WalletCell — иконки lock-open/lock + q-tooltip + контраст zero
Реестр кошельков → Пайщики: ячейка с двумя суммами (доступно/заблокировано)
была без подписей и читалась как «две одинаковые цифры». Иконки coins/lock
не передавали смысл «открыто/закрыто».

- Иконки: fa-lock-open (доступно) ↔ fa-lock (заблокировано) — симметричная
  пара, узнаваемая без объяснений.
- q-tooltip над каждой строкой: «Доступно» / «Заблокировано» (delay 200ms).
- value-zero / cell-dash: подняли контраст до rgba(0,0,0,0.55) на light и
  rgba(255,255,255,0.7) на dark — раньше нули сливались с фоном на обеих
  темах.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 14:21:45 +00:00
coopops ba4aed6e83 [@ant] fix(desktop): WalletCell стили вынесены в non-scoped block
`WalletCell` в ParticipantWalletsPage рендерится через render-функцию
inline-компонента — у его h()-узлов нет data-v parent'а, поэтому
scoped + :deep до них не доходит стабильно. Цвета (var(--q-positive),
rgba для zero/dash) и body--dark overrides не применялись — на странице
оставался хардкод-вид по умолчанию.

Решение: вынести правила `.wallet-cell` в отдельный `<style lang="scss">`
(без scoped). Класс достаточно специфичен — конфликта с другими
компонентами не будет.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 14:16:46 +00:00
coopops 146f950b43 [@ant] feat(controller+desktop): cooperativePrograms через GraphQL
ADR: фронт не ходит в чейн напрямую. fetchTable(soviet::programs) был
оставлен в двух местах после прошлой итерации — теперь убираем.

Controller:
- SovietBlockchainPort.getPrograms(coopname) + реализация в адаптере.
- AgreementService.getCooperativePrograms(coopname).
- Query cooperativePrograms (без auth-guard — публичный конфиг кооператива).
- DTO CooperativeProgramDTO {id, coopname, program_type, is_active, draft_id}.

SDK:
- regen schema.gql + zeus.
- Selector cooperativeProgramSelector.
- Query Queries.Agreements.CooperativePrograms.

Desktop:
- entities/Wallet/api: loadUserProgramWalletsData теперь дёргает
  client.Query(CooperativePrograms) вместо fetchTable.
- entities/Wallet/model: ICoopProgramData (полная chain-запись) заменён
  на минимальный ICoopProgramSummary {id, title, program_type, is_active?,
  draft_id?} — UI использует только эти поля + title из cooptypes registry.
- extensions/reports/.../participant-wallets-api.ts: то же самое для
  таблицы «Пайщики» в Реестре кошельков.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 13:43:25 +00:00
coopops 8fb7694185 [@ant] feat(cooptypes+desktop): реестр программ ЦПП + чистка цветов в Реестре кошельков
Стол совета:
- Удалён старый /soviet/ledger ("Реестр кошельков"). Новый реестр живёт
  в Отчёты ФНС → /reports/wallets (entities/Ledger2 + GraphQL).
- Снесены сопутствующие файлы (pages/Cooperative/ListOfLedgerAccounts,
  widgets/LedgerAccounts, entities/LedgerAccount) — внешних потребителей нет.

Реестр программ ЦПП (cooptypes/src/ledger2/programs.ts):
- TS-only массив LEDGER2_PROGRAMS с короткими (`short_label`) и полными
  (`display_name`) метками: ЦПП Цифровой кошелёк, ЦПП Маркетплейс,
  ЦПП Генератор, ЦПП Благорост.
- helper getProgramLabel(id) / getProgramShortLabel(id) с fallback на
  `Программа №<id>`. Менять централизованно тут, не в чейн-таблицах.

Применение в UI:
- ParticipantWalletsPage.vue: заголовок колонки программы = display_name
  из реестра (а не chain-поле title).
- entities/Wallet/api: program_details.title в loadUserProgramWalletsData
  подменяется на display_name из реестра.

Цвета (theme-aware):
- Хардкод #f5f6f8/#e0e0e0/#222/#ccc/#2e7d32/#8d6e63/#bbb в
  ParticipantWalletsPage заменён на var(--q-positive)/--q-warning и
  rgba с body--dark overrides.
- text-grey-6/7 заменён на свой класс caption-muted (rgba + body--dark)
  в Coop/Participant/Transfer pages — quasar text-grey-X не реагирует на
  body--dark и плохо читается на тёмной теме.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 13:16:51 +00:00
coopops e415c9ab0a [@ant] fix(wallet): signagree принимает candidate'ов + пишет в реестр документов
Симптом: при «Подтвердить платёж» в реестре платежей bundle регистрации
(createaccount + reguser + completeincome + signagree) падал с
"Пайщик не найден в кооперативе" — wallet::signagree вызывал
get_participant_or_fail, а в этом bundle participant ещё не создан
(создаётся позже в soviet::confirmreg → soviet::addpartcpnt после
голосования совета).

Решение: симметрично с soviet::sndagreement убираем проверку participant.
Доверие — на require_auth(coopname) + get_cooperative_or_fail +
verify_document_or_fail + get_program_or_fail. Точно та же модель доверия,
что у sndagreement.

Дополнительно: пишем подписанный документ в реестр документов через
Soviet::make_complete_document — чтобы программные соглашения отображались
в общем off-chain реестре документов кооператива (как непрограммные через
sndagreement). Добавлена константа Names::WalletActions::SIGN_AGREEMENT.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 12:33:23 +00:00
coopops 21e94ce0ed [@ant] fix(controller): bundle регистрации роутит программные соглашения через wallet::signagree
AccountBlockchainAdapter.registerBlockchainAccount пушил все agreements как
soviet::sndagreement в одном tx — после гейта Эпика 2 такие actions с
program_id > 0 контракт активно отвергает, и вся регистрация (createaccount +
registeruser + completeincome + agreements) откатывалась с
"программные соглашения подписываются через wallet::signagree".

Симптом: «Подтвердить платёж» в реестре платежей роняет всю транзакцию
регистрации.

Решение: один lookup soviet::coagreements на bundle, формируем map
agreement_type → ICoopAgreement, затем для каждого agreement из конфига:

- program_id == 0 → soviet::sndagreement (как раньше);
- program_id > 0  → wallet::signagree с program_id/draft_id из coagreement.

wallet::signagree требует существующего пайщика (get_participant_or_fail).
В bundle регистрации это гарантировано предыдущим registeruser action в той
же транзакции — actions исполняются последовательно.

Логика теперь идентична AgreementInteractor.sendAgreement (один источник
правды для роутинга).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-06 10:18:51 +00:00
coopops fdf526cc5e [@ant] feat(controller+desktop): cooperativeAgreements/agreementTemplates через GraphQL
Убираем прямые fetchTable из desktop entities/Agreement (ADR: фронт не
ходит в чейн напрямую — всё через controller). Это последний шаг для
корректной работы виджета RequireAgreements: вместе с фиксом type-поля
программных DTO (предыдущий коммит) фронт теперь видит подписанные
соглашения и не показывает повторный диалог.

Контроллер:
- AgreementService: getCoopAgreements (через SovietBlockchainPort.getCoagreements)
  и getAgreementTemplates (через BLOCKCHAIN_PORT.getAllRows для draft::drafts —
  глобальные scope=draft + per-coop, объединение).
- AgreementResolver: 2 новые Query — `cooperativeAgreements(coopname)` и
  `agreementTemplates(coopname)`. Без auth-guard'ов: данные публичные
  (конфиг кооператива и шаблоны документов).
- 2 DTO: CoopAgreementDTO, AgreementTemplateDTO.

SDK (regen schema + zeus + новые selectors/queries):
- Queries.Agreements.CooperativeAgreements
- Queries.Agreements.AgreementTemplates

Desktop:
- entities/Agreement/api/index.ts: fetchTable → client.Query.

Контракты, фронтовый виджет, остальные fetchTable не трогали.
2026-05-06 09:59:56 +00:00
coopops d325fea626 [@ant] fix(controller): программный agreement DTO отдаёт реальный type из coagreements
Раньше programmatic-DTO синтезировался с заглушкой type='programmatic'.
Виджет RequireAgreements на фронте матчит подписи через
userAgreement.type === coagreement.type ('wallet'/'blagorost'/...) — заглушка
никогда не совпадала, и пайщик после подписания снова видел диалог
«подпишите соглашение». Каждое нажатие 'Подписать' успешно делало upsert
через wallet::signagree (одна и та же программа, обновляются version/draft_id/
signed_at), но визуально ничего не менялось.

AgreementService теперь:
- Подгружает soviet::coagreements кооператива один раз на запрос (≤10 строк).
- Строит map program_id → type.
- programAgreementToDTO ставит type из map'а; fallback 'programmatic' только
  если коагримент по этой программе не настроен (теоретический случай).

SovietBlockchainPort.getCoagreements (множественное) выделено из существующего
getCoagreement; getCoagreement теперь его потребитель.

Контракты, GraphQL-схема, фронт — без изменений.
2026-05-06 09:45:24 +00:00
coopops b9c7fedbfb [@ant] feat(controller): stub-кошельки программ для подписанных соглашений без L3-баланса
После Эпика 3 ledger2::userwallets хранит только non-zero записи (контракт
стирает row при достижении нуля), и подписавший соглашение пайщик без
переводов не видел свой кошелёк — UX-регрессия по сравнению с legacy
soviet::progwallets.

Теперь WalletInteractor.assembleProgramWallets:
1. Берёт ожидаемые (username, program_id) из wallet::users.programs[] через
   USER_AGREEMENT_REPOSITORY.
2. Объединяет с L3-rows из ledger2::userwallets как раньше.
3. Для каждой пары без L3-row создаёт stub с нулями в валюте кооператива.
4. Сэмпл asset-а для zeroAssetLike берётся из существующего L3-row либо из
   coop.initial через BLOCKCHAIN_PORT.getCooperative; fallback '0.0000 RUB'.
5. block_num и timestamps stub'а — из programs[].signed_at (детерминированно).

Split ЦК (w.wal.share + w.wal.member) сворачивается в один entity как раньше.
Marketplace (program_id=2) кошельков не имеет, фильтруется через cooptypes
Ledger2.walletNamesForProgram(pid).length === 0.

Контракты, GraphQL-схема, фронт — без изменений.
2026-05-06 09:37:08 +00:00
coopops 6e26f36780 [@ant] fix(desktop): SignAgreementDialog подписывает соглашения через GraphQL
Раньше диалог делал прямой `transact` → `soviet::sndagreement` от имени пайщика.
После Эпика 2 программные соглашения (program_id > 0) пишет `wallet::signagree`,
требующий `coopname@active` — пайщик не может подписать такую транзакцию из
браузера, контракт ожидаемо отвергал.

Теперь идёт через GraphQL-мутацию `sendAgreement` (тот же путь, что у капитал-
extension через `useSendAgreement`). Контроллер читает `coagreement.program_id`
и сам выбирает action: `wallet::signagree` для program_id > 0, `soviet::sndagreement`
для непрограммных. Подписи пайщика на документе сохраняются и проверяются
контрактом.

Заодно убрал лишний JSON.stringify(meta) — GraphQL принимает meta объектом,
сериализацию делает контроллер при сборке chain-action.
2026-05-06 09:06:19 +00:00
coopops 0497cded09 [@ant] feat(cooptypes): codegen реестра кошельков из C++ wallets.hpp
`LEDGER2_WALLET_REGISTRY` и `LEDGER2_USER_SHARED_PROGRAM_MAPPING` теперь
вытягиваются из `contracts/cpp/lib/core/ledger2/wallets.hpp` Node-парсером
(`scripts/gen-from-cpp.ts`) и пишутся в `src/ledger2/wallets.generated.ts`.
Источник истины — C++; TS — копия. Парсер строгий: на любую неясность кидает
ошибку. На страже — snapshot-тест в `test/wallets-registry.snapshot.test.ts`.

Запуск: `pnpm --filter cooptypes gen:from-cpp` (или автоматически через
`prebuild` хук перед `pnpm --filter cooptypes build`).

Удалены локальные копии маппинга:
- `controller/src/domain/wallet/utils/program-wallet-mapping.ts` (был дубликат)
- inline `PROGRAM_TO_WALLET` в `migrator/migrations/049_*.ts`

Потребители теперь импортируют `Ledger2.walletNamesForProgram`,
`Ledger2.programIdForWallet`, `Ledger2.MEMBERSHIP_WALLET_NAME`,
`Ledger2.ALL_PROGRAM_WALLET_NAMES` из cooptypes.
2026-05-06 08:37:45 +00:00
coopops 5062f9edb2 [@ant] fix(controller): роутить sendAgreement на wallet::signagree при program_id > 0
После Эпика 2 soviet::sndagreement отвергает программные соглашения
(program_id > 0), а фронт зовёт его одинаково для всех типов. Контроллер
теперь читает coagreements кооператива и для program_id > 0 уходит в
wallet::signagree (coopname@active), оставляя soviet::sndagreement только
для непрограммных. Фронт менять не нужно.
2026-05-06 06:47:04 +00:00
coopops 1110b85224 [@ant] fix(migrator): сохранять membership_contribution при миграции progwallets → userwallets
В первоначальной версии 049 для program_id=1 (ЦК) писался только
w.wal.share с available/blocked, а membership_contribution молча терялась
(на текущем prod она 0, но тест-стенды и будущие данные содержат
ненулевые значения).

Теперь для ЦК эмитим ДВА migrate3-вызова: w.wal.share (available/blocked)
и w.wal.member (membership_contribution). Если membership=0 —
ledger2::migrate3 (0,0) делает безопасный no-op.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 12:16:17 +00:00
coopops 3030cf0174 [@ant] fix(controller): пагинация непрограммных соглашений по 1000 за страницу
Валидатор PaginationUtils ограничивает limit ≤ 1000; getAgreements падал
с HttpApiError при загрузке wallet.agreements в desktop. Заменил один
запрос с limit=10000 на цикл по страницам.

Обнаружено визуальной проверкой через docs-harness auth/signin.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 12:15:14 +00:00
coopops 48d40e77f0 [@ant] test(boot): edge-кейсы wallet::users + ledger2::migrate3 (story 16)
Добавлены интеграционные тесты на live-блокчейне:
- wallet::signagree повторно с тем же program_id → обновляет doc_hash без дубля.
- wallet::revokeagree без записи users → throws.
- wallet::revokeagree program_id не в programs[] → throws.
- ledger2::migrate3 идемпотентность (двойной вызов не дублирует).
- ledger2::migrate3 с blocked > 0 → blocked сохраняется отдельно.
- ledger2::migrate3 (0,0) когда записи нет → no-op.

Каждый тест содержит свой setup/cleanup (ensureNoProgram/ensureNoUserWallet),
чтобы порядок запуска не влиял на корректность.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 11:16:59 +00:00
coopops 3af6cf3f2b [@ant] feat(desktop): соглашения и программные кошельки через GraphQL (story 11/12)
- entities/Wallet: loadUserAgreements/loadUserProgramWalletsData → GraphQL
  (читают объединённый источник из соответствующих резолверов).
- entities/Agreement: убраны мёртвые loadAgreementsOfAllParticipants и
  loadSingleUserProgramWalletData; store сужен до фактически используемых полей.
- WalletsPage: participant-wallets-api тянет программные кошельки через GraphQL.
- RequireAgreements: сравнение версий через Number() (template.version из BC —
  string, userAgreement.version из DTO — number).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 11:12:52 +00:00
coopops 46baeb2857 [@ant] feat(controller): резолверы читают wallet::users + ledger2::userwallets (story 9/10)
AgreementService.getAgreements объединяет два источника (Эпик 2):
- непрограммные (program_id == 0) из soviet::agreements3 через AgreementRepository
- программные из wallet::users.programs[] через UserAgreementRepository
Программные соглашения разворачиваются в плоский ряд AgreementDTO
(synthetic id отсутствует, document лежит в action data, status=CONFIRMED).

WalletInteractor.getProgramWallets/getProgramWalletsPaginated читают из
ledger2::userwallets (UserWalletRepository) и агрегируют split-кошельки:
для program_id=1 (ЦК) собирает w.wal.share + w.wal.member в один
ProgramWalletDTO с membership_contribution из w.wal.member.

PROGRAM_ID_TO_WALLET_NAMES в domain/wallet/utils синхронизирован с
LEDGER2_USER_SHARED_PROGRAM_MAPPING в C++ контрактах и migrator/049.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 10:57:05 +00:00
coopops 1e80757588 [@ant] feat(controller): sync wallet::users + ledger2::userwallets (story 7/8)
UserAgreement (Эпик 2 / wallet::users): доменная сущность owner'а
программных соглашений с массивом programs[] (jsonb), full sync-цепочка
поверх AbstractEntitySyncService — coopname берётся из delta.scope.

UserWallet (Эпик 3 / ledger2::userwallets): доменная сущность L3-учёта
по USER_SHARED-кошелькам, sync с уникальным id и индексом
(coopname, wallet_name, username).

Контракт-info сервисы wallet/ledger2 регистрируются параллельно
SovietContractInfoService; новые репозитории и sync-сервисы подключаются
в TypeOrmModule.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 10:56:53 +00:00
coopops 2ac0bc7bf7 [@ant] test(boot/ledger2): L3 + wallet::users + migrate3 — sanity и integration (story 1.4 / эпики 2-3)
Sanity (cooptypes regen):
- Ledger2Contract.Actions.{Walletop,Migrate3} + Tables.UserWallets экспортируются
- WalletContract.Actions.{SignAgreement,RevokeAgreement,Migrate3} + Tables.Users экспортируются
- OPERATION_REGISTRY содержит USER_SHARED-операции

Integration (live blockchain после reboot:extra):
- wallet::signagree → users[username].programs[] обновлён
- wallet::migrate3 идемпотентность (без дубля программ)
- ledger2::migrate3 на USER_SHARED (w.cap.blago) → userwallets создан
- ledger2::migrate3 с (0,0) → userwallets запись удалена
- ledger2::migrate3 на COOPERATIVE (w.reg.entry) → fail с USER_SHARED check
- wallet::revokeagree → программа удалена; пустой vector → erase users

Тесты — точка контроля (pre-flight gate, NFR18):
запуск этого набора + миграций 047/048/049 на staging-дампе prod
с diff = 0 копеек до production rollout.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 10:29:11 +00:00
coopops 9fb53901aa [@ant] feat(migrator): per-coop self-service миграции agreements + L3 (story 2.5/3.6/3.7)
Три миграции через ledger3-релиз rollout:

- 047_migrate_agreements_to_wallet.ts — Эпик 2 / story 2.5
  agreements3.program_id>0 (status=confirmed) → wallet::migrate3.
  Идемпотентно, без удаления исходных записей (Эпик 4 финального
  deploy soviet).

- 048_migrate_phase1_minshare.ts — Эпик 3 / story 3.6 (ADR-008)
  participants[status=accepted] → ledger2::migrate3 на w.reg.minshr.
  amount = coop.org_minimum для type=organization, иначе coop.minimum.
  w.reg.entry не затрагивается — он COOPERATIVE без L3-разбивки.

- 049_migrate_phase2_progwallets.ts — Эпик 3 / story 3.7
  progwallets → ledger2::migrate3 с маппингом program_id → wallet_name:
    1 (ЦК)        → w.wal.share (membership_contribution=0 на prod)
    3 (Генератор) → w.cap.gen
    4 (Благорост) → w.cap.blago
  Pre-flight gate (NFR18) выполняется внешним скриптом сравнения
  Σ progwallets vs Σ userwallets перед production rollout.

src/utils:
- listCoops — обход registrator::coops с фильтром is_cooperative+active
- fetchAllRows — пагинированное чтение get_table_rows с lower_bound

Все три миграции per-coop self-service, batched по 50 actions/tx,
идемпотентные (migrate3 — overwrite, не +=).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 10:26:35 +00:00
coopops 48eac68c2b [@ant] feat(cooptypes): regen — wallet::users, ledger2::userwallets, walletop(username), migrate3 (story 1.4 / Эпик 2-3)
interfaces/wallet.ts:
- IUser, IProgramAgreement (table users)
- ISignagree, IRevokeagree, IWalletMigrate3 (новые actions)

interfaces/ledger2.ts:
- IUserWallet (table userwallets)
- IWalletop с username (расширен; story 3.1)
- IMigrate3 для ledger2 (story 3.3)

contracts/wallet:
- actions/{signAgreement,revokeAgreement,migrate3}.ts
- tables/users.ts

contracts/ledger2:
- actions/{walletop,migrate3}.ts
- tables/userwallets.ts

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 10:13:34 +00:00
coopops 3f0c4e672d [@ant] feat(soviet): запретить программные соглашения (program_id>0) в sndagreement/confirmagree/declineagree (story 2.6)
После Эпика 2: программные соглашения (program_id > 0) переехали в
контракт wallet (wallet::signagree / revokeagree / migrate3). soviet
остаётся owner-ом только не-программных соглашений (program_id == 0).

- sndagreement: проверка coagreement.program_id == 0 (иначе → wallet::signagree)
- confirmagree: проверка agreements2[id].program_id == 0
- declineagree: проверка agreements2[id].program_id == 0 (отклонение программных
  через wallet::revokeagree)
- migrateagree: остаётся (миграция структуры agreements → agreements2)

Программные записи из soviet::agreements3 удалит per-coop migrator (story 2.5).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 10:11:06 +00:00
coopops a2a984857e [@ant] feat(ledger2): cross-contract check wallet::users + post-mutation Σ L3 == L2 (story 3.2)
Контрактный assert L3 ⊆ L2 USER_SHARED — последняя линия защиты инварианта (NFR2).

- LEDGER2_USER_SHARED_PROGRAM_MAPPING: маппинг wallet_name → required_program_id
  (хардкод-таблица рядом с LEDGER2_WALLET_REGISTRY; ADR-004)
  - w.reg.minshr → 0 (исключение, без проверки соглашения)
  - w.wal.share / w.wal.member → 1 (ЦК)
  - w.cap.blago → 4 (Благорост)
  - w.cap.gen → 3 (Генератор)
- ledger2_required_program_id: helper с runtime check на отсутствие маппинга
  для USER_SHARED-кошелька (защита от пропуска при добавлении нового кошелька)

walletop:
- Pre-flight cross-contract READ wallet::users[username].programs[] для
  USER_SHARED-сторон (исключение w.reg.minshr через required_program_id == 0);
  fail-fast до мутаций
- Post-mutation Σ L3.{available,blocked} == L2.{available,blocked} на каждом
  затронутом USER_SHARED-кошельке (O(N_users), но это критичный assert)

apply:
- username обязателен для USER_SHARED на нормальном пути (НЕ-миграционные
  operation_code); исключение — o.mig.*

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 10:08:41 +00:00
coopops 9e72d596a6 [@ant] feat(ledger2): action migrate3 + L3-зеркало в revert (story 3.3)
migrate3 — идемпотентная per-record миграция L3-балансов:
- Заполняет userwallets[coopname][wallet_name, username] (overwrite, не +=)
- Без бух-проводок (это инициализация state, не операция)
- Без cross-contract check wallet::users.programs[]
  (миграция допускается ДО переезда соглашений; rollout-окно)
- Auto-delete при (available=0, blocked=0)
- Только USER_SHARED-кошельки (compile-time check на runtime)
- Auth coopname@active, payer coopname (NFR11)

L3-зеркало в revert — без изменений семантики: revert уже принимает
username и пробрасывает в walletop, который для USER_SHARED применяет
mirror op к L3-записи того же пайщика. Эпик 3 / story 3.3 покрывается
существующим путём.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 10:04:45 +00:00
coopops a2043ceffe [@ant] feat(ledger2): таблица userwallets и walletop(username) — L3 учёт (story 3.1)
Третий уровень учёта (L3) — пользовательские балансы на USER_SHARED-кошельках.

- Новая таблица userwallets {wallet_name, username, available, blocked}
  scope=coopname, payer=ledger2 (TODO D2 → coopname через linkauth)
- Composite key by_userwallet (combine_ids), индексы byuser/bywallet
- walletop расширен параметром username; передаётся из apply/walmove/revert
- USER_SHARED-сторона + username → upsert/delete L3 запись
- COOPERATIVE-сторона → username игнорируется
- Пустой username на USER_SHARED → L2-only mode (для совместимости со старым
  ledger2::migrate, который агрегирует без разбивки по пайщикам;
  полноценное заполнение L3 — через ledger2::migrate3 per-record, story 3.3)
- Auto-create L3 при первом ISSUE/TRANSFER/UNBLOCK
- Auto-delete при обнулении (available + blocked == 0)

НЕ входит в story 3.1 (вынесено в 3.2):
- cross-contract check wallet::users.programs[]
- post-mutation assert Σ L3 == L2

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 10:02:13 +00:00
coopops 782683916c [@ant] feat(wallet): таблица users и actions signagree/revokeagree/migrate3 (Эпик 2 / story 2.1)
Контракт wallet — owner программных соглашений (ADR-008).

- Новая таблица users {username, programs[]} (scope=coopname, payer=coopname)
- program_agreement: program_id, doc_hash, version, draft_id, signed_at
- Документ соглашения НЕ в state — только хэш и метаданные;
  полный текст лежит в action data signagree (audit trail)
- signagree: upsert по (username, program_id); auth coopname@active;
  проверки кооператива/пайщика/программы/draft_id
- revokeagree: удаление программы из vector; пустой vector → erase users;
  auth coopname@active
- migrate3: идемпотентная per-record миграция из soviet::agreements3
  без проверок программы/документа (заполняет state как есть);
  auth coopname@active

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 09:54:51 +00:00
coopops b23b743935 [@ant] fix(boot/tests): processDecision голосует тремя членами совета
Тесты с processDecision (walmove.test.ts → registerUser, capital.test.ts через
investInProject/withdrawContribution/registerExpense, registrator.test.ts)
прогоняются на стенде после `pnpm run reboot:extra`, который создаёт
расширенный совет из 5 человек: ant + petr + anna + mikhail + olga
(см. infra.ts § installInitialData с isExtended=true).

Soviet-контракт требует консенсус по большинству — 3+ голоса из 5. Старая
реализация processDecision голосовала только от ant (1 голос), и контракт
отвечал «Консенсус совета по решению не достигнут» в soviet::authorize.

Голосуем тремя (ant chairman + 2 member): минимум для прохождения. Все
члены используют один и тот же default_public_key (см. infra.ts:407 —
changeKey всем установлен config.default_public_key), поэтому подпись
chairman-WIF удовлетворяет authorization для всех трёх actor.

Проверено на стенде:
  • walmove.test.ts                  3/3 ✓ (было 2/3 — фейл AC1)
  • ledger2-wallets-registry.test.ts 14/14 ✓
  • ledger2-migrate.test.ts          10/10 ✓
  • ledger2-read-layer.test.ts        5/5 ✓

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 09:05:44 +00:00
coopops b4dfb38bf5 [@ant] test(ledger2): sanity+integration реестра кошельков и WalletOp
Покрывает super-story 1.1+1.2+1.3 (commit 44305a5b3f):

Sanity (12 тестов, без чейна — pure cooptypes):
  • LEDGER2_WALLET_REGISTRY = 11 шт. (5 USER_SHARED + 6 COOPERATIVE)
  • Никаких stale-имён (sharid/bginv/gncom/bgrid/wal.cash)
  • getWalletKind корректен для каждого имени
  • USER_SHARED naming convention w.<contract>.<waltype>
  • WalletOp без WALLET_ONLY/REVOKE
  • wallet_from/wallet_to ⊆ финальный реестр (плюс null)
  • zero_accounts_iff_both: debit==null ⇔ credit==null (ADR-003)
  • o.cap.invest = TRANSFER без бухпроводок (ADR-009)
  • capital ops используют только w.cap.{blago,gen,loan}
  • o.mig.rid удалён
  • o.adj.* (walmove/rev) корректные adjustment-операции

Integration (2 теста, blockchain ledger2::wallets):
  • on-chain wallets ⊆ финальный реестр (нет stale, нет вне-реестровых)
  • после регистрации пайщика появляются w.reg.minshr (USER_SHARED)
    и w.reg.entry (COOPERATIVE)

Прогнано на стенде mono-ai-3 (test-mode контракты):
  • ledger2-wallets-registry  14/14 ✓
  • ledger2-migrate           10/10 ✓
  • ledger2-read-layer         5/5  ✓
  • walmove                    2/3  (1 fail на soviet-консенсусе — не связан)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 08:11:33 +00:00
coopops 44305a5b3f [@ant] feat(ledger2): финальный реестр кошельков, WalletKind и упрощённый WalletOp
Super-story 1.1+1.2+1.3 эпика «L3 в ledger2» — атомарный релиз без коротких
итераций (ADR-009, ADR-010, ADR-002, ADR-003).

Реестр кошельков (cooptypes/ledger2/wallets.ts, contracts/lib/core/ledger2/wallets.hpp):
  • Финальный набор: 5 USER_SHARED + 6 COOPERATIVE = 11 кошельков
  • Введён WalletKind (USER_SHARED / COOPERATIVE) — обязателен для L3-разреза
  • USER_SHARED: w.reg.minshr, w.wal.share, w.wal.member, w.cap.blago, w.cap.gen
  • COOPERATIVE: w.reg.entry, w.wal.wthdrw, w.sov.infra, w.sov.delgte,
                 w.cap.loan, w.mkt.payout
  • Compile-time static_assert user_shared_naming_convention (base32 префикс w.)
  • Удалён w.wal.sharid (РИД-часть на legacy 80 — не существует ни у кого)
  • Унифицированы программы Благорост/Генератор: w.cap.blago и w.cap.gen
    взамен w.cap.bginv/w.cap.gncom/w.cap.bgrid

WalletOp cleanup (operations.hpp / operations.ts):
  • 5 значений: ISSUE / TRANSFER / BLOCK / UNBLOCK / BURN
  • WALLET_ONLY удалён — TRANSFER без бухпроводок маркируется
    (debit==null && credit==null) на уровне OPERATION_REGISTRY
  • REVOKE удалён — BURN покрывает оба сценария (штатное сжигание и mirror revert,
    различие через operation_code o.adj.rev)
  • static_asserts: zero_accounts_iff_both, burn_pattern_correct
  • Удалена операция o.mig.rid вместе с РИД-веткой migrate.cpp
  • migrate.cpp теперь жёстко проверяет legacy::accounts[80] == money-часть
    с явным сообщением «закрыть РИД до миграции» (страховка)

Capital — единые программные кошельки (ADR-009):
  • 5 операций o.cap.* переведены на w.cap.blago / w.cap.gen
  • Стандарты p.cap.invest, p.cap.prop, p.cap.rid обновлены под унифицированные имена
  • o.cap.invest: TRANSFER без бухпроводок (раньше WALLET_ONLY)
  • Константы BLAGOROST_INVEST/RID → BLAGOROST_FUND, GENERATOR_COMMIT → GENERATOR_FUND

Controller / cooptypes:
  • resolveWalletAccountId переведён на (debit==null && credit==null)
  • IRevert.mirror_wallet_op: 4=BURN (вместо 5=REVOKE)
  • Doc-комментарии обновлены под новые имена

Standards-site / desktop UI:
  • WalletOp type без WALLET_ONLY/с BURN
  • Граф/FocusBar: hasPosting и условия отображения переводов упрощены
  • WalletTransferDialog: resolveAccountId fallback по (debit==null && credit==null)

Boot тесты:
  • capital.test.ts: WALLET_GENERATOR_FUND / WALLET_BLAGOROST_FUND
  • ledger2-migrate.test.ts: SHARE_FUND_RID удалён из ассертов
  • walmove.test.ts: комментарии под новые имена

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 06:27:38 +00:00
Alex Ant edd9f3ff91 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-05-04 20:48:17 +05:00
coopops 244ff15e19 Merge branch 'dev' into reports 2026-05-04 11:27:06 +00:00
coopops f017c9dbd5 [@ant] ci(publish-docs): триггерить из reports и marketplace2
standards-site публикуется на gh-pages вместе с остальной докой. Чтобы
изменения стандартов из reports/marketplace2 попадали в превью на
docs.coopenomics.world/standards/, добавляем эти ветки в push-триггер.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-04 11:26:57 +00:00
coopops 2f1b8a5897 Merge branch 'dev' into reports
# Conflicts:
#	.gitignore
#	components/contracts/cpp/lib/consts.hpp
#	components/contracts/cpp/wallet/p.wal.depo.standard.yaml
#	components/contracts/standards-site/src/components/FocusBar.vue
#	components/cooptypes/src/common/names/index.ts
2026-05-04 11:23:58 +00:00
coopops 92b01297f6 [@ant] chore(standards): убрать устаревшие YAML из dev — актуальные в reports
В dev эти 4 standards-yaml заморожены 23 апреля. В reports они с 24-го
переименованы и переписаны (префиксы o./p., стиль C, шлифовки). Удаляем
их в dev, чтобы при мердже dev → reports пришли актуальные версии без
конфликтов. reg.adduser/reg.recovery в reports пока нет — будут заведены
заново под новую конвенцию по необходимости.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-04 11:22:18 +00:00
coopops 9b6cadb3be update blockchain to latest tag 2026-05-01 11:57:57 +00:00
coopops 0d043bc58a [@ant] fix(boot/setContract): ENOENT → soft warn, остальные ошибки → fail-fast
Полный fail-fast ломал dev-сборку bootcoop: ledger2 живёт пока в ветке
reports, в dev закомментирован в components/contracts/CMakeLists.txt
и не попадает в dicoop/contracts:dev. boot:remote падал на ENOENT
ledger2.wasm, хотя в dev контракт временно не нужен.

Компромисс:
- ENOENT (отсутствующий wasm/abi) — console.warn + return.
  Когда ветка reports мержится в dev → CMakeLists раскомментирует ledger2
  → dicoop/contracts:dev его подтянет → bootcoop установит автоматически,
  без правок в boot. No merge conflicts.
- Все остальные ошибки (RPC, transaction reject, abi parse) — re-throw
  обогащённой Error: имя контракта, target, путь, cause. Это поведение
  для production-relevant сбоев остаётся как в предыдущем коммите.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 10:25:33 +00:00
coopops 360619332b [@ant] fix(boot): fail-fast при ошибке деплоя контракта в setContract + dicoop/blockchain:latest
Раньше Blockchain.setContract молча проглатывал ENOENT (отсутствующий
wasm/abi) и любые ошибки api.transact: console.log + return. boot:remote
завершался exit 0 даже когда часть контрактов не установилась —
sideboot мог отдать "готовую" цепь с дырами в развёртывании.

Изменения:
- await на api.transact (раньше fire-and-forget — ошибки транзакций
  тоже не ловились, только синхронные fs.readFileSync)
- catch перебрасывает обогащённой Error: имя контракта, target-аккаунт,
  путь к артефакту, причина (через cause). startInfra прерывается
  в startInfra → boot:remote → exit 1.

SIDEBOOT.md: dicoop/blockchain_v5.1.1:dev → dicoop/blockchain:latest
во всех ссылках (таблица артефактов + compose snippet).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 10:19:13 +00:00
coopops 72c824f5a2 [@ant] docs(boot): SIDEBOOT.md — инструкция для агентов в соседних репо
Краткий quickstart для AI-агентов и людей, которым нужна локальная
EOSIO-нода + контракты в стороннем репозитории (parser2,
blockchain-protocol) для интеграционных тестов, без mono-инфры.

Содержит:
- список артефактов в hub (blockchain_v5.1.1, contracts, bootcoop) и
  правила тегов
- минимальный docker-compose snippet (~30 строк)
- источник конфигов ноды (components/boot/src/configs/)
- команды запуска и чистого перезапуска (down -v + rm blockchain-data)
- проверка готовности через get_code на всех ожидаемых аккаунтах
- опциональные mono-data флаги (INSTALL_*_DATA)
- куда смотреть в коде если что-то не работает
- известные ограничения (boot:remote не падает на missing wasm,
  dicoop/contracts ребилдится только при изменении контрактов)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 10:16:34 +00:00
coopops 04f028b96b [@ant] fix(boot/Dockerfile): не мерджить cooptypes.deps + --legacy-peer-deps
ERESOLVE падал на @typescript-eslint/parser@^7.8.0 (cooptypes.deps)
требующем peer eslint@^8, а у boot.devDeps eslint@^9.

Cooptypes — type-only пакет, его одна prod-dep (@typescript-eslint/parser)
в runtime не нужна. Убираю мердж cooptypes.deps. Только factory.deps
мерджу в boot.dependencies.

Дополнительно --legacy-peer-deps на npm install — на случай других
peer-конфликтов в transitive graph factory'а.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:41:44 +00:00
coopops 8607840581 [@ant] fix(boot): мерджить factory/cooptypes deps в boot pkg.json + failOnWarn:false
Inline workspace-deps cooptypes/factory тянет в bundle их транзитивные
npm-зависимости (factory: handlebars, ajv, mongodb, nunjucks, pdf-lib,
moment-timezone, uuid, json-schema, inline-css). unbuild warning'ит
эти как "implicit external" и при failOnWarn:true роняет билд.

Фикс:
- build.config: failOnWarn:false — warnings допустимы
- Dockerfile: после build мерджим factory.deps + cooptypes.deps в
  boot/package.json. Boot.deps побеждают в случае коллизии. Так
  npm install --omit=dev в runtime поставит всё что транзитивно
  нужно для inlined factory кода.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:39:06 +00:00
coopops ef951b9291 [@ant] fix(boot): inline только workspace-deps, npm-deps external + npm install
Полный bundle (inlineDependencies:true) упал на native binding
cpufeatures.node — dockerode тянет ssh2 → cpu-features → нативный
.node файл, который rollup не может включить в bundle.

Компромисс:
- workspace-deps cooptypes/factory bundle'ятся inline через rollup hook
  (через external override) — иначе они теряются при npm install
  (workspace:* specifier'ы в package.json)
- npm-deps остаются external — нативные binaries сохраняются как есть
- runtime: npm install --omit=dev ставит только prod npm-deps

Финальный образ ~270MB:
- node:22-slim ~75MB
- dist (boot bundle с inlined workspace-deps) ~250K
- node_modules только prod npm-deps
- /contracts ~3MB

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:36:26 +00:00
coopops f42359e2fd [@ant] fix(boot/build.config): rollup hook для реального inline всех deps
unbuild 2.0.0 имеет баг: options.externals.push(...pkg.dependencies)
выполняется ДО проверки inlineDependencies, поэтому inlineDependencies:true
de-facto не работает — всё из package.json остаётся external. Bundle
получался ~200K с require('commander'), require('pg') и т.д., и в
финальном образе всё падало.

Обход: hook 'rollup:options' переопределяет external напрямую, делая
external только Node built-ins. Всё остальное inline'ится в bundle.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:32:24 +00:00
coopops 8faa6ea3a6 [@ant] fix(boot): full-bundle через inlineDependencies:true → образ ~150MB без node_modules
Прошлая попытка (inlineDependencies массивом строк) не сработала —
unbuild 2.0.0 принимает только boolean. После build factory всё ещё
require'ился из node_modules, и образ падал.

Переключил на inlineDependencies:true — bundling ВСЕХ deps (workspace
+ npm) внутрь одного dist/index.cjs. В финальной runtime-стадии больше
нет npm install и node_modules — только COPY одного файла bundle и
COPY /contracts.

Ожидаемый размер ~100-150MB (node:22-slim ~75MB + bundle).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:29:36 +00:00
coopops 08fff7cca2 [@ant] fix(boot): slim runtime через inline workspace-deps + npm install --omit=dev
Прошлый образ занимал 1.5GB на диск из-за pnpm storage в /deploy/node_modules/.pnpm
(deploy --legacy не отфильтровал devDependencies).

Двухсторонний фикс:

1. boot/build.config.ts: добавил rollup.inlineDependencies для cooptypes
   и @coopenomics/factory — workspace-deps теперь bundle'ятся прямо в
   dist/index.cjs, в node_modules финального образа их не нужно.

2. boot/Dockerfile: заменил pnpm deploy на classic npm install --omit=dev
   в runtime-стадии. В builder перед копированием стираем cooptypes/factory
   из package.json (они уже в bundle), npm зову без --frozen-lockfile —
   pnpm-lock.yaml для npm бесполезен. Финальный образ содержит:
   - dist/index.cjs (boot bundle ~200K с inlined workspace-deps)
   - node_modules только prod npm-deps (mongoose/pg/eosjs/...)
   - /contracts (~3MB)

Ожидаемый размер ~250MB на диск против 1.5GB.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:25:48 +00:00
coopops 7675877251 [@ant] fix(boot/Dockerfile): билдить транзитивные workspace-deps перед deploy
Smoke-test pulled dicoop/bootcoop:dev упал на "Cannot find module
'@coopenomics/factory/dist/index.cjs'". Причина: pnpm deploy --prod
копирует node_modules в /deploy через симлинк-разрешение, а у
workspace-зависимостей factory/cooptypes ссылка идёт на dist/, который
не был собран — звался только pnpm build для самого boot.

Замена: pnpm --filter "@coopenomics/boot..." build — троеточие тащит
транзитивные workspace-deps (cooptypes, factory), у обоих unbuild
конфиги, dist/ генерится корректно.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:17:29 +00:00
coopops bd1e27b069 [@ant] fix(boot/Dockerfile): slim multi-stage образ только с dist + prod-deps
Предыдущая версия тащила весь workspace в финальный образ (~1.5GB).
Перепилил в три стадии:

  1. builder   — full workspace + pnpm install + unbuild build → dist/
                 + pnpm deploy --prod --legacy /deploy (self-contained)
  2. contracts — dicoop/contracts:<tag> alias
  3. runtime   — node:22-slim + COPY /deploy + COPY /contracts

В финальном образе остаётся только:
  - dist/index.cjs (unbuild-бандл boot)
  - node_modules только prod-зависимостей (без dev)
  - /contracts (~40MB)

ENTRYPOINT прямо вызывает node dist/index.cjs — без pnpm/esno-обёртки,
быстрее старт, меньше зависимостей.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:09:37 +00:00
coopops 983e02a139 [@ant] fix(boot/Dockerfile): self-contained build без зависимости от mono-base
dicoop/mono-base тегается только под semver-релизы (build-containers.yaml
триггерится на refs/tags/*), поэтому :dev/:testnet/:main отсутствуют —
bootstrap workflow упал на pull этого тега.

Перепилил Dockerfile: COPY весь workspace из текущего checkout'а +
pnpm install --filter "@coopenomics/boot..." (тащит boot + транзитивные
cooptypes/factory). .dockerignore отрезает node_modules/dist/blockchain-data.

Workflow упростился — pull только dicoop/contracts, MONO_BASE_TAG больше
не нужен.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:04:56 +00:00
coopops b0bbe05c56 [@ant] feat(boot): dicoop/bootcoop образ для sideboot в соседних репо
Цель: в соседних репозиториях (parser2, blockchain-protocol и т.д.)
для тестов и отладки нужно поднимать только цепь + контракты, без
mono-инфры (mongo/postgres/desktop). Решение — два контейнера в их
compose: dicoop/blockchain (нода) + dicoop/bootcoop (one-shot bootstrap).

Что добавлено:
- components/boot/Dockerfile — multi-stage от dicoop/contracts:<tag>
  (контракты flat-layout в /contracts) + dicoop/mono-base:<tag>
  (runtime с pnpm/node + workspace). ENTRYPOINT = pnpm run boot:remote.
  CONTRACTS_DIR=/contracts выставлен по умолчанию.
- .github/workflows/build-bootstrap.yaml — push в dev/testnet/main
  билдит и пушит dicoop/bootcoop:<branch> + :latest для main +
  :<branch>-<short-sha> для пинов. Telegram нотификации.
- components/boot/README.md — раздел про sideboot с готовым compose
  snippet'ом, переменными окружения и опциональными INSTALL_*_DATA.

Версионирование dicoop/bootcoop:<tag> совпадает с dicoop/contracts:<tag>
(multi-stage из того же тега) — контракты и bootstrap синхронны.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 09:02:21 +00:00
coopops 3cc86331bf [C28-8][@ant] docs(controller): project-context для AI-агентов по sync-архитектуре v1
Enforcement-выжимка из ARCH: Синхронизация узла с блокчейном v1 +
ARCH: Интеграция контроллера с parser2 v1 (оба в _blago/13/components/14).
~80 правил в 14 секциях: composite-entity namespaced (db/bc/derived),
dispatch pipeline (dedup → save → wake → emit), write-mutation через
pool.submitWithPool + waitForDelta + subscription, read-path = PG only,
fork через ForkRegistry sequential, pool state machine с placeholder
pattern + OrphanPendingReconciler, anti-patterns.

Claude Code автоподхват при работе в controller/. Source of truth —
ARCH-документы в blago; этот файл — только enforcement layer.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 08:20:32 +00:00
Alex Ant 8539b1e6fd chore(release): publish 2026-04-30 22:09:52 +05:00
Alex Ant 477779c984 chore(release): publish 2026-04-30 21:45:21 +05:00
Alex Ant 9491b6356d Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-04-30 21:45:02 +05:00
coopops df062ea271 refactor(prod-runtime): сервисы стартуют без devDeps + вернули prune
Теперь все production-сервисы запускаются изнутри dicoop/mono-base
без volume-mount и без devDeps:

- @coopenomics/parser: scripts.start `esno src/index.ts`
  → `node ./dist/index.cjs` (unbuild уже собирал dist).
- @coopenomics/notifications: scripts.sync `tsx src/sync/sync-runner.ts`
  → `node ./dist/sync/sync-runner.cjs`. Добавлен entry
  `src/sync/sync-runner` в build.config.ts — unbuild делает
  bundle с разрешёнными импортами (старый tsc-output ломался
  под чистым node из-за extension-less ESM-импортов).
  Поле `bin.novu-sync` обновлено на `.cjs`.
- @coopenomics/controller: `tsconfig-paths` перенесён из devDeps
  в deps. Сервис стартует через `ts-node -r tsconfig-paths/register`
  (ts-node уже был в deps). После prune --prod оба останутся.

В корневом Dockerfile вернули `pnpm prune --prod --ignore-scripts`
после lerna run build — выкидывает все devDeps (typescript, vitest,
unbuild, eslint, quasar, tsx, esno и пр.).

Smoke-test slim-образа `dicoop/mono-base:dev-local` (2.96GB):
- parser → дотягивает до runtime, валится на missing NODE_ENV ✓
- notifications → стартует, валится на missing NOVU_API_KEY ✓
- desktop → дотягивает до runtime, валится на missing chain url ✓
- boot --help → работает ✓
- coopback (controller) → ts-node компилирует, стартует ✓

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 16:17:59 +00:00
Alex Ant 0a95748580 chore(release): publish 2026-04-30 20:41:03 +05:00
Alex Ant cab6be45b3 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-04-30 20:40:41 +05:00
coopops 615052e4ec fix(docker): откат pnpm prune --prod до фикса scripts.start
cooparser стартует через `esno src/index.ts` (esno = devDep) и
notifications — через `tsx src/sync/sync-runner.ts` (tsx = devDep).
В playbook'е monocoop pull-based деплой (docker-compose.containers.yaml)
запускает их без volume-mount, изнутри образа. После prune --prod
оба упали бы на старте с `esno: not found` / `tsx: not found`.

mono-base остаётся ~5GB (вместо 3GB после prune). Полное сжатие
вернём отдельным шагом — после того как cooparser и notifications
переведём на `node dist/...`.

Multi-stage сама по себе уже даёт win: 7.36GB → ~5GB через
.dockerignore + apt --no-install-recommends + python3-only-runtime
без gcc/dev-headers.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 15:38:08 +00:00
Alex Ant 59b25c2995 chore(release): publish 2026-04-30 20:28:51 +05:00
Alex Ant adc8790c3e Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-04-30 20:28:32 +05:00
coopops 726d0c620e chore(docker): multi-stage mono-base + testnet smoke-stack (story 6.1)
Корневой Dockerfile переписан под две стадии: builder с full toolchain
(apt dev-headers, WeasyPrint в venv, pnpm install + lerna run build +
pnpm prune --prod --ignore-scripts) и runtime — slim node:22-slim
без gcc/dev-headers, только runtime-libs WeasyPrint + готовый /app.

Локально сжалось с 7.36GB до 2.95GB (-60%). Образы наследники
(dicoop/desktop / coopback / cooparser / notificator / notifications)
автоматом получат тонкий runtime через build-containers.yaml.

Безопасность для playbook'ов monocoop: их docker-compose.yaml собирает
сервисы из components/{controller,parser,desktop}/Dockerfile (не
корневого) и монтирует ./:/app — корневой mono-base туда вообще не
попадает.

.dockerignore — выкинул .git (962MB), blockchain-data/wallet-data,
_blago, coverage, *.log и т.п. Build-context теперь намного легче.

docker-compose.testnet.yml — локальный 3-сервисный smoke-стек:
ke-node (dicoop/blockchain_v5.1.1:dev) + ke-contracts (one-shot
copy из dicoop/contracts:dev в shared volume) + ke-bootstrap
(mono-base, node /app/components/boot/dist/index.cjs boot:remote).
Изолирован от dev-ноды mono-ai-4-node-1 через отдельную сеть и порты
8919/9907/8101.

В playbook'ах не применяется (там docker-compose.yaml, не .testnet.yml).

.gitignore — добавлен .env.testnet (содержит EOSIO_*KEY).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 15:21:17 +00:00
coopops 30af7cd90e revert(boot): откат отдельного dicoop/bootstrap образа
Boot — это и есть бутстрап. Дубликат через отдельный образ создаёт
второй workflow и две точки сборки там, где для testnet/prod достаточно
запустить existing pnpm -F @coopenomics/boot run boot:remote внутри
dicoop/mono-base:<tag>, который уже собирается через build-containers.yaml.

Что остаётся в dev (полезное из предыдущих коммитов):
- boot:remote команда — без dockerode, для сценария когда нода
  поднята отдельным сервисом docker-compose.
- CONTRACTS_DIR env-driven path в configs/contracts.ts — позволяет
  монтировать dicoop/contracts:<tag> как volume.
- "build" script в boot/package.json для unbuild.

Удалено:
- components/boot/docker/ (Dockerfile + entrypoint + bootstrap.package.json
  + bootstrap.pnpm-workspace.yaml)
- .github/workflows/build-bootstrap.yaml

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 13:07:35 +00:00
coopops 01c6a2689a chore(boot): bootstrap-образ публикуется в DockerHub (dicoop/bootstrap)
Симметрия с dicoop/contracts и остальными dicoop/* образами;
GHCR делает first-publish приватным и требует ручного visibility-toggle.
DockerHub-секреты DOCKERHUB_USERNAME / DOCKERHUB_TOKEN уже используются
build-contracts.yaml и build-containers.yaml.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 12:32:21 +00:00
coopops 44d76bf317 fix(boot): объявить main + files для pnpm deploy
Без явного `files` поля `pnpm deploy --prod` не копирует dist/ в /app
(unbuild создаёт его, но pnpm считает не-входящим в публикуемый
артефакт). Из-за этого ENTRYPOINT bootstrap-образа не находил
/app/dist/index.cjs на стадии Verify.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 11:23:22 +00:00
coopops 0b68538061 fix(boot/docker): мини-workspace вместо корневого pnpm-workspace.yaml
Корневой /package.json ссылается на 14 workspace-пакетов (cleos,
controller, desktop, ...), которые в build-context bootstrap-образа
не копируются — pnpm install падает с ERR_PNPM_WORKSPACE_PKG_NOT_FOUND.

Решение: положить рядом с Dockerfile минимальные bootstrap.package.json
и bootstrap.pnpm-workspace.yaml, в которых workspace = только
[boot, cooptypes, factory]. pnpm install идёт с --no-frozen-lockfile
(локфайл генерится прямо в build-stage, drift безопасен — финальный
образ запинен через branch+sha теги).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 11:19:59 +00:00
coopops 6a924bd7ee fix(boot/docker): ARG CONTRACTS_TAG до первого FROM
BuildKit делает ARG, объявленный после FROM, локальным для предыдущей
стадии — поэтому FROM dicoop/contracts:${CONTRACTS_TAG} ругался
'invalid reference format'. Глобальный ARG до всех FROM фиксит.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 11:15:19 +00:00
coopops 6d89303544 feat(boot): ke-bootstrap docker image + boot:remote режим (story 6.1)
Образ ghcr.io/coopenomics/bootstrap для one-shot первичного деплоя
контрактов на KE-узел в docker-compose. Соответствует решению из
project_ke_bootstrap_strategy: boot/contracts собираются в mono,
apps-catalog только потребляет готовые образы.

Состав:
- components/boot/src/index.ts — команда `boot:remote`: ждёт RPC
  по CHAIN_URL, вызывает startInfra() через eosjs (без dockerode).
  Опциональные initial-data/extra-data через env-флаги.
- components/boot/src/configs/contracts.ts — env-driven CONTRACTS_DIR.
  Когда задан — flat layout /contracts/<name>/<name>.{wasm,abi}
  (как в dicoop/contracts), иначе старые относительные пути.
- components/boot/package.json — script `build` (unbuild) +
  `boot:remote` для локального запуска.
- components/boot/docker/Dockerfile — multi-stage:
  deps → build (cooptypes/factory/boot) → pnpm deploy --prod →
  COPY --from=dicoop/contracts:<tag> → node:20-alpine slim runtime.
- components/boot/docker/entrypoint.sh — режимы boot:remote / verify
  / shell + проверка обязательных env'ов.
- .github/workflows/build-bootstrap.yaml — публикация в GHCR по push
  в dev/testnet/main + verify smoke-test после push'а.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 11:14:09 +00:00
coopops dec2162142 fix(inter): set publishConfig.access=public for first publish
E402 при первой публикации @coopenomics/inter — npm требует
явный access:public в package.json (lerna-глобальный access
не действует на первый scoped-publish).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 09:18:45 +00:00
Alex Ant 6796ed4109 chore(release): publish 2026-04-30 14:10:28 +05:00
Alex Ant 4f9ff0c1d3 chore(release): publish 2026-04-30 14:10:04 +05:00
Alex Ant 055830b4a9 fix whitelist 2026-04-30 14:09:36 +05:00
Alex Ant 74deacf957 Merge branch 'dev' of github.com:coopenomics/mono into dev
Made-with: Cursor

# Conflicts:
#	components/blago-cli/package.json
#	components/boot/package.json
#	components/cleos/package.json
#	components/contracts/package.json
#	components/controller/package-lock.json
#	components/controller/package.json
#	components/cooptypes/package.json
#	components/desktop/package.json
#	components/docs/package.json
#	components/factory/package.json
#	components/inter/package.json
#	components/migrator/package.json
#	components/notifications/package.json
#	components/parser/package-lock.json
#	components/parser/package.json
#	components/sdk/package.json
#	components/setup/package.json
#	lerna.json
2026-04-30 14:08:02 +05:00
coopops 8d5f2129ae chore(release): publish 2026-04-30 08:55:23 +00:00
coopops 0ace1e45d7 Merge branch 'dev' into testnet 2026-04-30 08:42:36 +00:00
coopops c7e1b7762c feat(cooptypes,boot): TS-интерфейсы контракта apps + boot deploy
Контракт apps (каталог приложений ВОСХОД) теперь:
- разворачивается через mono boot (account apps + setContract из
  build/contracts/apps);
- имеет TS-обёртку в cooptypes — Actions/Tables/Interfaces по
  паттерну остальных контрактов, AppsContract в общем индексе.

interfaces/apps.ts написан вручную, потому что eosio-abi2ts 1.2.2
не парсит optional-типы (name?, checksum256?) из action setcoop.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-30 08:42:23 +00:00
coopops 5865f6fc14 feat(contracts/apps): smart-contract каталога приложений + docker pipeline
Контракт `apps` (координационная плоскость для apps-catalog):
- 4 таблицы: packages, releases, subs, coops; ABI 21 KB, WASM 70 KB
- 11 actions: regpackage, transferpkg, setrelease, reactivate, withdraw,
  cleanup, regsub, expsub, regcoop, setcoop, migrate
- subs.chain_id и coops.chain_id — каноническая идентификация подсети
- coops.signing_key — отдельный subnet-signing-key (не active),
  ротация через setcoop без потери ранее выпущенных JWT
- releases с TTL retention 90 дней + inline cleanup до 50 записей
- atomic supersede в setrelease — выполняет FR8 «approve → ACTIVE»
  на стороне blockchain'а

CI контейнер `dicoop/contracts`:
- упаковывает все 21 контракт (15 user + 6 system eosio.*) в alpine 10.8 MB
- список контрактов берётся из CMakeLists (single source of truth)
- триггер push на dev/testnet/main + workflow_dispatch
- маппинг ветка→tag: dev/testnet/main + sha-pinned tag для воспроизводимости
- manifest.json с sha256 каждого артефакта внутри образа
- entrypoint: copy [name] | manifest | sha256 | list | ls
- multi-stage потребление в ke-bootstrap = 0 MB на VPS

Закрывает блокер Story 6.x (KE bootstrap) для apps-catalog.
2026-04-30 07:55:06 +00:00
coopops ccf3023ed7 [989-9][@ant] fix(blago-cli/format): не парсить body внутри matter.stringify
serializeBlagoMarkdown звал matter.stringify(body, data) — gray-matter сначала парсит body как frontmatter; story с описанием, начинающимся с «---», ловилась как фронтматтер и валила js-yaml на строках с двоеточием (`Authorization: Bearer <token>`). Теперь сериализуем заголовок отдельно (matter.stringify('', data)) и сами клеим body; подрезаем лишний хвостовой `\n`, чтобы etag оставался стабильным между pull'ами.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-29 16:54:27 +00:00
coopops c7515d9bbf [989-9][@ant] refactor(ledger2/migrate): voskhod-ветка как явный хардкод-таблица
Заменил компьютацию (compute_min_total_by_type, sum_progwallet_available,
sum_progwallet_blocked, чтение legacy_861) на 5 const-констант с суммами,
которые правятся прямо в файле при необходимости. Удалил sum_progwallet_available
— больше не нужна.

Бух-баланс таблицы: Dr 51 = 614 200, Cr 80 = 601 700, Cr 86 = 12 500;
Σ Dr = Σ Cr ✓.

Прочие кооперативы — без изменений (по-прежнему через share_money / rid_share
+ compute_min_total_by_type).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-29 13:47:58 +00:00
coopops 94f5b7f56b [989-9][@ant] fix(ledger2/migrate): min_total по типу пайщика + voskhod-ветка по фактам
Расчёт минимального паевого учитывает тип: organization → coop.org_minimum,
иначе → coop.minimum (фолбэк на minimum, если org_minimum/type не выставлены).
Кэш active_participants_count больше не используется — он не несёт разбивку
по типу.

Для voskhod добавлена отдельная ветка миграции по фактическим суммам
progwallets (legacy::accounts и progwallets рассинхронизированы): Σ pid=1
→ w.wal.share, Σ pid=4 → w.cap.bginv, Σ pid=3 → w.cap.gncom; вступительные
из legacy_861, мин. паевые расчётно. TRANSIT_RID для voskhod не шлём —
имущество остаётся осадком на legacy 80 до Phase 2 (ADR-009).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-29 12:57:05 +00:00
coopops 42b0acd014 [989-9][@ant] fix(registration): не дублировать уведомление о регистрационном платеже
В PaymentDomainEntity добавлен транзиентный isNewlyCreated — true когда
платёж создан вот сейчас, false когда поднят существующий PENDING через
findActivePendingPayment. RegistrationService шлёт sendNewInitialPayment
только при isNewlyCreated=true, поэтому повторные мутации фронта (reload,
immediate-watch на step) больше не плодят 7 одинаковых сообщений
председателю. Поле не пишется в БД и не уходит в DTO.
2026-04-29 06:12:26 +00:00
coopops e5ac552d12 [989-9][@ant] fix(wallet): закрыть createDepositPayment для не-active пайщиков
ActiveUserStatusGuard точечно на мутации createDepositPayment — пайщик до
приёма советом (status≠active) получает 403 вместо ушедшей в обработку
заявки. На фронте сама кнопка «Совершить взнос» скрыта в DepositButton
по тому же признаку — не водим пользователя по тупиковому пути.
2026-04-29 06:12:15 +00:00
coopops 0cfd56ab87 [989-9][@ant] fix(docs-harness/project-create): вкладка «Компоненты» вместо обхода через Мастерскую
Предыдущий обход (после `setStatusActive` уходить в Мастерскую и
кликать компонент из общего списка) был оправдан только тем, что
вкладка «Компоненты» проекта отдавала «Нет компонентов». Корень оказался
не в clearance — controller компоненты не фильтрует, доступ на чтение
открыт всем. Это race с парсером: после `capital::startproject`
mongo-parser ещё не успевал обработать дельту проекта, и
`capitalProject`-resolver возвращал `components: []`. Через 3-5 секунд
тот же запрос отдавал список как надо.

Теперь в шаге 11:
1. После `setStatusActive` ждём 3с — даём парсеру довести startproject.
2. Кликаем вкладку «Компоненты».
3. Ждём до 30с появления компонента в списке (строгий waitFor).
4. Только потом кликаем по нему.

Скриншот 06-component-page-active обновился — это тот же экран, что
снимался обходным путём, разница только в навигации.
2026-04-28 20:44:54 +00:00
coopops 7778777a02 [989-9][@ant] feat(docs/blagorost): два пути адаптации — председатель и пайщик
UI Capital extension к этому моменту переехал: «Адаптация к работе с
программой "Благорост"» теперь живёт в CapitalOnboardingCard для
председателя, а пайщику показывается мастер регистрации
(CapitalRegistrationPage). Старый сценарий искал заголовок
«Адаптация» на странице регистрации — там его уже нет, председательский
путь падал, пайщиковый и не предполагался.

Разделил на два сценария:

1. **adaptation** (пайщик newadapter) — мастер регистрации:
   01-roles → 02-time-resource → 03-rate → 04-about → 05-documents.
   Используется новая фикстура newadapter (Сидоров А. М.), которая
   намеренно остаётся БЕЗ Capital-регистрации (фаза 05 не запускается),
   чтобы UI открыл ей мастер. Подписание документов в самом сценарии не
   делается — иначе при повторном прогоне мастер не покажется.
   adaptation.md полностью переписан.

2. **adaptation-chairman** (новая страница) — карточка для председателя
   с пятью шагами и кнопками «Объявить собрание совета» + диалог
   «Предложение повестки». Кадры: 01-overview, 02-propose-dialog.
   Содержание adaptation-chairman.md описывает приём советом пяти
   документов программ ГЕНЕРАТОР и БЛАГОРОСТ.

Поддержка инфраструктуры:
- shoot.mjs: добавлена фикстура newadapter (Сидоров А. М.) в
  KNOWN_FIXTURES — фабричный пайщик без Capital-регистрации.
- seed-capital phase 02-reset-onboarding: обнуляет в постгресе
  onboarding_*_done и удаляет onboarding_*_hash в extensions.capital.
  Без неё bootExtra() через initExtensionsInPostgres ставит все done=true
  как dev-shortcut, и UI считает онбординг председателя завершённым
  (CapitalOnboardingCard прячется). Нужен прямо обратный 02-extension-config
  — поэтому отдельная фаза, а не модификация старой.
- shoot-blagorost-all.mjs: adaptation-chairman добавлен в очередь перед
  adaptation, чтобы успеть снять CapitalOnboardingCard до того как
  следующие сценарии через 02-extension-config зальют все done=true.
- adaptation.mjs: исправлены селекторы (.hour-option через nth(3),
  без невалидной запятой в waitForSelector).
2026-04-28 20:22:02 +00:00
coopops 3e09bab448 [989-9][@ant] fix(docs-harness/blagorost): починил project-create + перегенерил скрины
project-create: после клика «Создать» в диалоге компонента сценарий
ждал по `text=MVP v1`, который матчился прямо в открытом диалоге (поле
«Название компонента») и проскакивал мимо реального события закрытия.
Теперь явно ждём пока модалка с заголовком «Название проекта» /
«Название компонента» исчезнет из portal-диалогов. Если за 20с не
закрылась (парсер отстал на свежей цепочке) — закрываем Esc'ом и идём
дальше: компонент уже создан на chain, ждать UI бесполезно.

Также для шага 11 (вход в компонент) перестали ходить во вкладку
«Компоненты» проекта — председатель сам только что создал проект,
clearance к нему ещё нет, и страница отдаёт «Нет компонентов».
Возвращаемся в Мастерскую и кликаем компонент из общего списка.

adaptation: подписан wallet-онбординг через DOM-цикл с ожиданием
появления каждого нового диалога (CapitalRegistrationPage монтируется
раньше первого диалога, готовый dismissOnboardingDialogs выходил
сразу). Wallet-онбординг теперь честно проходится, но **сценарий всё
равно падает**: в текущем UI (CapitalRegistrationPage.vue) старого
заголовка «Адаптация к работе с программой» больше нет — председателю
показывается заглушка «Ранним участникам», пайщикам — мастер выбора
ролей. Это переработка сценария + adaptation.md под новый UI, выходит
за scope текущего фикса.
2026-04-28 19:30:07 +00:00
coopops 3f073b4eec [989-9][@ant] docs(blagorost): перегенерировал все скриншоты + фиксы оркестратора
Прогон через `pnpm shoot:blagorost --reboot` — 12 из 14 сценариев
успешно. На обновлённых скринах больше нет кнопки «Принять участие
(J)» в правом нижнем углу там, где её не должно быть (artifacts /
voting / results) — фикс был добавлен в prepare ранее.

Скриншоты обновлены для: artifacts, clearance, commits, investments,
master-and-plan, profile, project-create (5/6, последний — старый),
projects-list, results, tasks, voting. Также свежий
commits/04-approve-dialog.png.

Оркестратор bin/shoot-blagorost-all.mjs:
- adaptation теперь идёт первым (страница «Адаптация» видна только до
  того, как любой 02-extension-config поставил *_done=true);
- между группой «до голосования» и «голосование/результаты» делается
  второй reboot — после commits-master компонент уходит в состояние,
  где seed-фаза 08-investments перестаёт быть идемпотентной и валится
  с «нужен rfrshsegment»;
- при выборочном --only=... reboot между группами не делаем —
  пользователь сам отвечает за состояние стенда.

bin/shoot.mjs: controller health-check 90с → 180с — после reboot:extra
coopback грузит контракты ~2 мин, 90с не хватало (первый сценарий
после --reboot падал на ECONNREFUSED).

Известные fail'ы (не блокеры):
- adaptation — на свежей цепочке у председателя горит wallet onboarding
  (privacy/wallet/signature/user), который перекрывает страницу
  «Адаптация». Нужна доработка сценария: либо снимать диалог, либо
  предварительно отмечать базовые agreements *_done. Старые
  скриншоты adaptation остались (не критично — проза не менялась);
- project-create — упал на финальном клике по компоненту, но первые 5
  кадров получены и положены в docs руками. 6-й остался от прошлой
  версии.
2026-04-28 18:47:11 +00:00
coopops 11db245757 [989-9][@ant] feat(docs-harness): pnpm shoot:blagorost — все скрины одной командой
Добавил bin/shoot-blagorost-all.mjs: оркестратор, который прогоняет все
сценарии docs/new/blagorost/** в порядке естественного жизненного цикла
компонента (profile → adaptation → … → result-submit → results).
--reboot применяется один раз на первом сценарии, дальше всё идёт по
накопительному стенду — seed-фазы идемпотентны, ничего не теряется.
После каждого успешного сценария — install в components/docs/.
Падение одного сценария не останавливает остальные; в конце сводка.

Алиас в package.json: `pnpm --filter @coopenomics/docs-harness shoot:blagorost`.

Параллельно: добавил `capital:07b-clearance-all` в prepare сценариев
artifacts.mjs / commits.mjs / results.mjs. Без него пайщик заходил на
страницу без допуска и в правом нижнем углу торчала кнопка «Принять
участие (J)» — критично, потому что некоторые из этих экранов реально
доступны только участникам с допуском (страница голосования, внесение
результата).
2026-04-28 17:31:06 +00:00
coopops aa52dfc268 [989-9][@ant] docs(blagorost): аудит — убрал техничку, упростил роли в задачах
Пользовательская документация в docs/new/blagorost/** не должна
светить контрактные действия, имена полей и внутренние термины. Прошёл
по всем страницам и убрал:

- capital::approvecmmt / pushrslt / pushresult / signact1/signact2 /
  refreshsegment / convertsegm / addproject / setmaster / setplan /
  startproject / openproject / createcmmt / startvoting / vote /
  removeproject — заменил на формулировки в терминах кнопок и статусов;
- available_for_program / available_for_wallet — переписал по смыслу
  (results.md, wallets.md);
- ResultSubmissionService.generateCombinedData / ResultDocumentPayloadV2
  / capital_results / SHA-256 / on-chain — убрал техничку про сборку
  РИД, оставил суть «отпечаток в блокчейне» (intellectual-property.md,
  artifacts.md);
- Project hash / parent hash / метаданные — снёс admonition «что не
  нужно заполнять руками» из project-create.md.

В lifecycle.md убрал отдельную колонку «Действие контракта» из «карты
переходов» — она дублировала «Что нажимает» техническими именами.

В tasks.md убрал избыточную матрицу разрешённых переходов, унифицировал
роли: «submaster / Ответственный» → просто «Исполнитель» (по сути это
главный исполнитель, но в пользовательской документации эту тонкость
не разворачиваем). Главных практических следствий и таблицы статусов
достаточно.
2026-04-28 17:30:53 +00:00
coopops 9dc8d3bbdd [989-9][@ant] feat(boot/seed-capital): фаза 15 + надёжный разнос actions в 07b
Phase 15 (15-active-component): готовит компонент «Минимальный продукт»
под проектом «Приложение Стол Заказов» в статусе Active без коммитов:
clearance + setmaster=ant + setplan + startproject. Состояние «работа
открыта, коммитов ещё нет» — для UI-проверок и docs-harness.

07b: поднял sleep между getclearance и confirmapprv с 700ms (1×block)
до 1500ms (≥3×block). Эмпирически 700ms ~1 раз из 6 терял строку в
capital_appendixes — мастер на UI видел «Принять участие» вместо
действий. Заплатка вокруг особенности SHIP, см. memory
project_parser_loses_appendix_deltas.md.
2026-04-28 16:59:51 +00:00
coopops 354c3f7f57 [989-9][@ant] docs(blagorost/tasks): синхронизировал текст с новым UI строки задачи
Тон вернул к зафиксированному стилю (живой «Вы», без техники):
- убрал q-select из описания статуса — теперь компактный chip с
  выпадашкой;
- словарь: «оценка часов» → «чип времени (факт/план)», «estimate» →
  «оценка», «Sidebar задачи» → «Страница задачи»;
- активные глаголы вместо безличных оборотов.

Доописал inline-действия со строки доски (после редизайна IssueListRow):
- клик по чипу статуса — выпадашка переходов;
- клик по чипу времени — редактирование оценки (для мастера);
- клик по аватаркам / «+» — выбор исполнителей.
Создание задачи — плавающая кнопка «+» в правом нижнем углу или
горячая клавиша T (вместо «кнопки в шапке доски»).

alt-описания скриншотов привёл в соответствие с реальным состоянием
(статус «Выполнена», счётчики «Моё время» и т.д.). Скриншоты не
перегенерировал — они актуальные после UI-фиксов 28 апреля.
2026-04-28 16:59:40 +00:00
coopops da49a64188 [989-9][@ant] feat(boot/seed-capital): честный онбординг через совет — без fakeDocument
Раньше «чистая мастерская» seed (01+02+04+04b) использовала
initExtensionsInPostgres() dev-shortcut — он клал в extensions.capital
ХАРДКОЖЕНЫЕ хеши шаблонов с *_done=true. UI считал онбординг пройденным
и пускал в Мастерскую, но как только пользователь шёл по любому
soviet-onboarding flow в реальной UI, controller'ные verify-утилиты
падали на «Сгенерированный документ с хешем X не найден» — потому что в
монге документов с такими хешами не было.

Чиню это полностью честно:

- index.ts: регистрирую phase 02b в диспетчере как `02b-real-onboarding`
  (было: только импортирована, но не подключена).

- phase 02b: проводит ВСЕ 5 шагов адаптации через настоящий soviet vote
  flow (Generate → Propose → 3×Vote → Authorize+Exec). Заменил fakeDocument
  на РЕАЛЬНУЮ генерацию протокола FreeDecision (registry_id=600) через
  Mutations.Documents.GenerateDocument с обязательными decision_id +
  project_id (из meta решения), потом client.Document.signDocument(...,
  CHAIRMAN, 1) — реальная подпись председателем. Чейн возвращает hash в
  lowercase, controller — UPPERCASE: case-insensitive lookup. Между
  votefor и FreeDecision генерацией — retry с pause (parser-индекс
  отстаёт ~700ms-3s, без него factory.getDecision падает на «Голоса за
  решение не найдены»). Перед отправкой meta стрингифай (eosjs strict).

- phase 04b: переписал на `Mutations.Chairman.ConfirmApprove` с РЕАЛЬНЫМ
  approved_document. Чтение оригинального approval.document из
  postgres.chairman_approvals (ant'ова подпись id=1), затем добавление
  второй подписи (signatureId=2) через client.Document.signDocument —
  ровно как делает desktop'овский useConfirmApproval. Retry на ожидание
  parser-индексации. fakeDocumentSignedBy выпилен.

Минимальный seed «чистая мастерская» теперь:
  reboot:extra (5 членов совета — нужны для голосов)
  → seed-capital 01-programs 02b-real-onboarding 04-contributor 04b-approve-contributor

Все хеши в pg/mongo соответствуют реальным документам — UI flow «Принять
договор УХД» больше не получает «не найден».

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 15:45:53 +00:00
coopops ef49bd0c61 [989-9][@ant] feat(boot/seed-capital): фаза 04b — approve УХД председателя
Phase 04 регистрирует Contributor через Capital flow, но УХД остаётся в
status=pending. При обычном boot:extra (5 членов совета) утверждение
проходит через стандартный flow голосования; для plain boot (один
председатель) этого не происходит — любая попытка обновить ставку/часы
валится с «Договор УХД с пайщиком не активен».

Новая фаза 04b делает один soviet::confirmapprv с approval_hash =
contributor_hash, подписанной председателем — УХД переходит в active.
Идемпотентно (no-op если уже active).

Минимальный «чистая мастерская» seed теперь:
  seed-capital 01-programs 02-extension-config 04-contributor 04b-approve-contributor

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 13:50:47 +00:00
coopops 8bc727b749 [989-9][@ant] fix(capital/issues-list): не клипать actions на узкой колонке
На ComponentTasksPage список задач делит экран с левой боковой панелью
(Статус/Мастер/Видео/Репозиторий) — реальная ширина списка ~600px CSS.
В таком layout actions-блок (chip статуса + аватарки) уезжал за правый
край: html-table без table-layout:fixed подгонял колонку под intrinsic
width содержимого, длинный title распирал строку шире контейнера.

- IssuesListWidget: table-layout: fixed; width: 100% + overflow: hidden
  на q-td — таблица заперта в контейнере, IssueListRow flex layout
  корректно ужимает title.
- IssueListRow: flex-wrap: wrap + title flex-basis 200px / min-width 200px
  — на достаточно широких контейнерах одна строка, на узких actions
  переезжает на вторую без клиппинга.
- tasks.mjs scenario description: пояснил, что в кадре 01-board виден
  новый компактный layout (приоритет → ID → чип времени → тайтл → chip
  статуса → аватарки).

Сценарий blagorost/tasks: 5 shots сняты успешно, аватарки центрированы,
title корректно ellipsis-ит на узких строках.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 13:22:48 +00:00
coopops 8af11032e0 [989-9][@ant] fix(capital/issues-list): оптимистичная смена статуса + фикс ширина исполнителей
- IssueStatusChip: оптимистичный UI — при выборе нового статуса chip
  перекрашивается мгновенно (через локальный optimisticStatus ref), не
  ждёт round-trip. Watch на props.modelValue сбрасывает override, когда
  store догоняет. Сохранение через saveImmediately (без 2s debounce) —
  статус discrete, не текст. На время round-trip — мини-спиннер в chip,
  ошибка → откат к предыдущему статусу.
- SetCreatorAvatars: триггер фикс-ширины 72px (2 аватарки + overflow «+N» =
  3 круга). Без фикс-ширины колонка прыгала row-to-row, статус-chip уезжал
  влево/вправо при разном числе исполнителей. visibleCreators сокращён с 3
  до 2 — дальше «+N» в одном кружке, чем 4 наезжающих инициала.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 12:39:05 +00:00
coopops 11804b5b7a [989-9][@ant] fix(capital/issues-list): расширил чип времени 70→86px
«2.5д/30ч» в одну строку без троеточия.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 12:28:45 +00:00
coopops 0a0c7ad246 [989-9][@ant] feat(capital/issues-list): инлайн-чип времени + чистые аватарки
- IssueTimeChip — фикс-ширины (70px) триггер с иконкой schedule + компактным
  «факт/план». Title больше не «прыгает» между задачами с разным estimate.
  Клик → q-menu с инпутом плана (estimate, debounce save через useUpdateIssue)
  и read-only факта с прогресс-баром. Факт не задаётся вручную (read-only,
  считается из TimeEntry) — это вынесено в hint в попапе.
- SetCreatorAvatars: q-avatar заменён на чистый div. Quasar внутри
  q-avatar__content использует position: absolute; inset: 0, и при наличии
  border на родителе содержимое визуально съезжает из центра. Свой div с
  display: flex; align-items: center; justify-content: center даёт ровный
  центр инициала.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 11:22:07 +00:00
coopops 16e802749f [989-9][@ant] fix(capital/issues-list): полировка строки задачи
- meta-блок теперь горизонтальный: приоритет → ID → время. Время с
  прогрессом без иконки-часов (no-icon в Estimation), не утяжеляет строку.
- Аватарки исполнителей укрупнены 22→28px; принудительный flex-center
  внутри q-avatar__content + box-sizing: border-box — инициалы по центру,
  не уезжают к правому-нижнему углу.
- Меню смены статуса: внутренние отступы (header «Сменить статус», padding,
  gap, hover, border-radius пунктов), маленький цветной кружок (q-icon
  circle) вместо «голого» badge.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 11:11:20 +00:00
coopops 43beb8fe90 [989-9][@ant] feat(capital/issues-list): компактный layout строки задачи + mobile
Переделал список задач: meta-блок (id + приоритет, под ними оценка/факт),
title растягивается на всё свободное пространство, действия справа сжаты до
chip-статуса и стопки аватарок исполнителей.

Новые компоненты:
- IssueStatusChip — маленький цветной chip-триггер; q-menu со списком разрешённых
  переходов (ровно те же permissions/allowed_status_transitions). Логика
  обновления через useUpdateIssue (debounce + откат при ошибке) — как в
  UpdateStatus.
- SetCreatorAvatars — стопка аватарок (до 3 + «+N»). По клику открывается q-menu
  с существующим ContributorSelector — multi-select / поиск / автосохранение
  через useSetCreators сохраняются.
- IssueListRow — общая строка для обоих режимов виджета (полноэкранный с
  virtual-scroll и компактный встроенный). Mobile-фолбэк на ширине ≤640px:
  meta+title в первой строке, action-блок переносится во вторую.

Старые UpdateStatus / SetCreatorButton оставил — они используются на
страницах деталей задачи; в списке заменены на компактные варианты.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 10:59:11 +00:00
coopops 6240b6971d [989-9][@ant] fix(capital/issues-list): колонка времени не наезжает на приоритет
Колонка estimate в IssuesListWidget зафиксирована (width 110px, flex-shrink 0,
overflow hidden) — Estimation с прогресс-баром больше не распирает соседнюю
колонку с заголовком/приоритетом. В Estimation у progress-bar убрал min-width
60px (заменил на width 100%/max-width 90px) и добавил min-width 0 на
контейнер — теперь компонент сжимается под родителя.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 09:30:01 +00:00
coopops 081894c3f8 [989-9][@ant] feat(docs/blagorost): инструкция «Задачи и процесс производства»
* tasks.md — Agile-механика внутри Компонента: 6 статусов (BACKLOG/TODO/
  IN_PROGRESS/ON_REVIEW/DONE/CANCELED), матрица переходов 6×6 с ролями
  Мастер/Ответственный/Исполнитель/Совет, права (только Мастер ставит
  estimate/priority и закрывает в DONE), два режима учёта времени —
  без estimate (час/час, поделено на активные задачи) и с estimate
  (estimate/N исполнителей при → DONE).
* mkdocs.yml — пункт «Задачи и план работ» в навигацию Благороста.
* doc-shoot scenarios/blagorost/tasks.mjs — 5 кадров: доска задач,
  диалог «Создать задачу», sidebar мастера и исполнителя, страница
  «Моё время» со счётчиками (Доступно / В ожидании / Подтверждено).
* seed-capital phase 09: задача estimate=0 в IN_PROGRESS — иллюстрирует
  почасовое начисление «время по факту» для исследовательских задач.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 08:19:13 +00:00
coopops 9a50a4317b [989-9][@ant] feat(blagorost): расширение инструкций + temp workaround SHIP intra-block deltas
* docs/blagorost: новые страницы — clearance, lifecycle, wallets; расширены
  artifacts (4 формата), voting (Водянов), results (внести результат, акт),
  commits (вид мастера); mkdocs.yml — навигация под них.
* docs-harness: 4 новых сценария (clearance, commits-master, result-submit,
  voting перепрошит); набор скриншотов под все 4 формата артефактов.
* seed-capital: фазы 07b-clearance-all, 09b-artifacts, 10a-pending-commit
  для seed чистого blagorost-стейта без ручных кликов.
* 07b: sleep 700ms между getclearance и apprvappndx — обходим SHIP-баг,
  при котором insert+erase contract_row внутри одного блока не эмиттит
  дельту (net state change = 0). См. memory project_parser_loses_appendix_deltas.
* controller: возвращена 3-сек задержка emit'а action-события — даёт
  дельтам того же блока (capital_appendixes) сохраниться раньше, чем
  обработчики action полезут читать состояние.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-28 08:19:12 +00:00
coopops 415edc183f [350-1][@ant] docs(standards/p.mkt.reqst): чище переформулировал — кооператив контрагент для обеих сторон
Убрал разговорную и поучительную интонацию, оставил суть деловым языком: кооператив принимает имущество у одного и передаёт другому, контрагентом для обеих сторон выступает сам кооператив.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 16:17:38 +00:00
coopops e664c8ec1d [350-1][@ant] docs(standards/p.mkt.reqst): не обмен между пайщиками, а проведение имущества кооперативом сквозь себя
Переформулировал purpose: «исполнение заказа» — это не обмен между пайщиками через платформу, а одновременное удовлетворение кооперативом двух потребностей (одного — поставить, другого — получить), стороны напрямую не взаимодействуют. Это суть кооперации.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 16:16:36 +00:00
coopops 45b065397e [350-1][@ant] chore(standards-site): убрал ненужный заголовок «Контракт, процесс, сущность, статус, стандарт»
В шапке страницы стандарта остаётся только сам абзац-вступление; тех. перечисление сущностей удалено как мусор.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 16:15:31 +00:00
coopops c306bff0ff [350-1][@ant] docs(standards): простые человеческие вступления (purpose) во всех остальных стандартах
Везде заменил многословный технический рассказ про действия / операции / wallet-коды / Дт-Кт на один абзац-смысл — что это за процесс, кто им пользуется и зачем. Детали уже есть в карточках действий, статусов и операций — повторять их в шапке избыточно.

Затронутые стандарты: p.wal.depo, p.wal.wthdrw, p.cap.invest, p.cap.debt, p.cap.prop, p.cap.rid, p.mkt.reqst, reg.coop, sov.authpkg, sov.decision, sov.selectbranch, meet.hold.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 15:38:45 +00:00
coopops dc77a3fa65 [350-1][@ant] feat(standards-site/ProcessGraph): рабочая область во всю доступную высоту
Высота диаграммы убрана из clamp-кепа 820px — теперь это calc(100vh - 240px) с min-height 520px. На мониторах 1440p+ диаграмма занимает всю доступную высоту, а не 2/3 экрана.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 15:18:11 +00:00
coopops 7cff3e0757 [350-1][@ant] feat(standards-site/FocusBar): операции в две колонки + Проводки/Переводы рядом
— На карточке действия с двумя операциями (типа confirmreg → o.reg.payent + o.reg.putmin) операции теперь сидят рядом в две колонки (grid auto-fit minmax 180px), а не стопкой.
— Внутри каждой операции «Проводки» и «Переводы» тоже разнесены в две колонки — компактные значения «Дт/Кт» и «∅ → wallet» больше не занимают по строке каждый.
— Колонке операций отдан больший вес во flex-раскладке (flex 1.5, min 280px), чтобы не уезжала на следующую строку, когда рядом ещё и блок документов.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 15:12:51 +00:00
coopops 519c3af14d [350-1][@ant] docs(standards/p.reg.accept): purpose — только смысл процесса, без дублирования карточек
Оставлен один абзац: что это за процесс и зачем он нужен. Детали (участники, операции, составная сущность) уже описаны в карточках действий, статусов и операций — повторять их в шапке избыточно.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 15:08:56 +00:00
coopops 888dd70704 [350-1][@ant] feat(standards-site): рассказ-вступление в шапку страницы, FocusBar не закрывает диаграмму на старте
— ProcessPage: новая секция «Контракт, процесс, сущность, статус, стандарт» над диаграммой; туда переехал длинный purpose с разрывом абзацев (white-space: pre-line). Краткий summary убран — он дублировался.
— FocusBar: режим process-start больше не рендерится — на свободном (не сфокусированном) состоянии диаграмма видна полностью; оверлей внизу появляется только когда выбрано действие, статус, документ или операция.
— p.reg.accept: actions[].purpose / states[].description / operations[].description обрезаны обратно до tagline (1–2 фразы) — карточки на диаграмме больше не «раздуваются».

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 15:06:16 +00:00
coopops fdf72fa858 [989-9][@ant] fix(docs/blagorost): один Акт приёма-передачи РИД с двумя подписями, не два акта
Терминологическая ошибка: я представлял приёмку РИД как «два акта»
(акт о результатах + акт приёма-передачи), но фактически это **один**
документ — Акт приёма-передачи РИД (`ResultContributionAct`), на
котором стоят **две подписи**: signact1 — пайщика, signact2 —
Председателя.

Заодно явно перечислены три документа всей приёмки:
  • Заявление о паевом взносе РИДом — пайщик подписывает на pushrslt;
  • Решение Совета о приёмке — стандартная цепочка через Совет;
  • Акт приёма-передачи РИД — единый документ, две подписи.

В таблице ролей `results.md`: «подписать два акта» → «подписать
Акт приёма-передачи РИД».

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 14:52:39 +00:00
coopops e4bffdf4f2 [350-1][@ant] feat(standards/p.reg.accept): двухуровневое описание (Стиль C) + «кассир» вместо «оператор Gateway»
— p.reg.accept переписан в стиле «tagline + развёрнутый абзац» для summary, purpose, actions[].purpose, states[].description, operations[].description, related[].note и scenario.steps[].description; сохранены все структурные поля.
— FocusBar: gateway_operator → «Кассир» в человеческих лейблах; .focus-bar__desc получил white-space: pre-line, чтобы пустая строка в YAML рендерилась как разрыв абзаца.
— p.wal.depo: «оператор Gateway» → «кассир» в прозе шага оплаты.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 14:51:30 +00:00
coopops e5e19dab86 [989-9][@ant] docs(blagorost): сверка терминов со словарём кооперативной экономики v1
Прошёлся по страницам Благороста и привёл термины к официальному
словарю (`components/blago-cli/_blago/.../c5-slovar-kooperativnoy-
ekonomiki-v1.md`):

  • «программа Благорост» → **ЦПП «Благорост»** (программа
    кооперативной НИОКР, куда уходит складочный капитал
    `contributors_bonus_pool`); «Главный кошелёк» (ровно по словарю).
  • «соавторы» (как множественное от Соавтор) → **Авторский
    коллектив** (Автор + Соавторы + Мастер) — там, где речь о
    распределении базы/бонусов на роли is_author. По словарю «Соавтор»
    — это конкретно экспертно-творческое участие; для общего пула
    точнее «Авторский коллектив».
  • Введён термин **Складочный капитал ЦПП «Благорост»** для
    обособленного учёта `contributors_bonus_pool` — это уже было в
    словаре, но в моих текстах не использовалось.
  • **Билет времени** — упомянут как учётная единица астрономического
    времени (ровно как в словаре).
  • В voting.md явно назван **метод Водянова (система «Компас»)** со
    ссылкой на Положение о ЦПП «Благорост».

Доля в ОАП — переформулирована как «закреплённая часть стоимости
ОАП, право требования возврата паевого взноса. **НЕ доход и НЕ
авторские права**» — точно по словарю и многократно повторённой
просьбе пользователя.

Формула стоимости РИД (intellectual-property.md) переписана под
словарные термины:
  A = (1 + φ) × (v + v′) × t  — генерационная часть (Исполнители +
                                Авторский коллектив, базы + бонусы)
  B = φ × A                    — Складочный капитал ЦПП «Благорост»
  total_contribution = A + B   — стоимость РИД, паевой взнос Компонента

Также добавлены термины в локальный словарь (файл .gitignore'нут,
живёт в blago-cli — не пушится с этим коммитом, но пользователь
может перенести их в исходный репо словаря): Артефакт, Астрономическое
время, Доля в ОАП, Общественно-полезное (созидательное) время,
Результат интеллектуальной деятельности (РИД).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 14:48:20 +00:00
coopops 752efc1480 [989-9][@ant] feat(docs/blagorost): инструкция «Артефакты» + «Результат интеллектуальной деятельности»
Две новые страницы документации Благороста:

«Артефакты» (`artifacts.md`):
  • Что такое артефакт — фрагмент описания работы (текст, диаграмма,
    схема), создаётся авторами и исполнителями.
  • Где живут — вкладка «Артефакты» на проекте (общие документы) и на
    компоненте (специфичные требования / диаграммы / мокапы).
  • Четыре поддерживаемых формата: Markdown (основной), Mermaid
    (отдельный артефакт-диаграмма), BPMN (бизнес-процессы), drawio
    (произвольные схемы); таблица «когда какой формат».
  • Как создать (диалог + Ctrl+Enter / ⌘+Enter).
  • Как они влияют на формирование РИД.

«Результат интеллектуальной деятельности» (`intellectual-property.md`):
  • Что такое РИД — формальный документ, не «ссылка на коммит». Состав:
    project.description + Stories (артефакты проекта/компонента) + Issues
    + Commits с git-дифами и текстом коммитов + meta.
  • Хэширование SHA-256 в `ResultSubmissionService.generateCombinedData()`,
    публикация хэша в blockchain через `capital::pushrslt`, хранение
    полного текста в БД `capital_results`.
  • Приёмка через два акта подписи: signact1 (пайщик подтверждает свой
    вклад) и signact2 (председатель принимает РИД от лица кооператива);
    между ними — формальное решение совета.
  • Стоимость РИД — формула с публичного сайта программы благорост:
    A = (1 + φ) × (v + v′) × t для генерационной части и B = φ × A для
    доли Благороста; φ = 0.618 (контракт-константа AUTHOR_BASE_COEFFICIENT).
  • Два класса времени: профессиональная компетенция (v) + общественно-
    полезное (v′), оба в единой ставке `hour_cost`.
  • Соавторы получают 0.618× базы исполнителей; бонусы голосования по
    методу Водянова добавляют ещё столько же.
  • Доля Благороста (`contributors_bonus_pool = 0.618 × total_generation_pool`)
    распределяется между всеми пайщиками программы пропорционально
    их предыдущим долям в ОАП — это «доля в объекте авторских прав»,
    не «доход» и не «авторские права».

Сценарий docs-harness `blagorost/artifacts.mjs` — два кадра (вкладка
«Артефакты» компонента и проекта). На seed-данных артефакты не
создаются, поэтому показ — пустой страницы с кнопкой создания.

`mkdocs.yml` — два новых пункта в разделе «Благорост»: «Артефакты»
и «Результат интеллектуальной деятельности».

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 14:39:49 +00:00
coopops f65edf4e00 [350-1][@ant] fix(standards/p.cap.rid): approverslt — то же заявление 1040 со второй подписью председателя 2026-04-27 14:32:36 +00:00
coopops 26a992f0b4 [350-1][@ant] feat(standards): расставить registry_id где есть шаблоны
- p.cap.prop: 1070 заявление + 1071 решение совета + 1072 акт ×2
  (имущественный взнос в Благорост-капитализацию)
- p.cap.debt: 1050 заявление + 1051 решение (двойная подпись:
  председатель → совет; в реестре одна форма GetLoanDecision)
- p.wal.wthdrw: 900 заявление + 901 решение (двойная подпись)

Поправлены и тексты под человеческие title из реестра. Поле template:
убрано — все три файла переходят на slim-схему с registry_id.
2026-04-27 14:29:49 +00:00
coopops 4205c57372 [350-1][@ant] fix(standards-site): кошельки по name (string) — починить «нет в реестре» и пустые ISSUE-источники
Реестр кошельков перешёл с числовых id на eosio::name-строки
(w.wal.share, w.cap.bgrid и т.д.) — UI был ещё в старой схеме:

- WalletId: number → string (соответствует cooptypes/ledger2)
- getWallet ищет по поле `name`, не `id`
- walletTitle: вывод meta.human_name (вместо meta.name = идентификатор)
- walletDisplayId / v-if «Переводы»: пустая строка == null → ∅
  (раньше пустая wallet_from при ISSUE прорывалась как пустая ячейка)
- reg.coop.standard.yaml: числовые 2001/3003 → w.wal.share / w.sov.delgte
2026-04-27 14:26:01 +00:00
coopops 286ea424d5 [350-1][@ant] feat(standards-site): человеческие заголовки в «Связанных стандартах»
Вместо технического process_type (`p.reg.accept`) показываем title
стандарта («Приём пайщика»), а сам код вынесен мелким моно-бейджем
сбоку. Relation-слова уже были по-русски.
2026-04-27 14:11:45 +00:00
coopops 1e5fabe088 [ledger2][@ant] fix(parser): Initializer принимает block_num — не теряет дельты при purge
Доразвитие фикса 3219459b8e. В прошлой версии при свежей БД
(`startBlock=1 && currentBlock=0`) я перенёс purgeAfterBlock внутрь
условия и не оставил его для производственного hot-restart-сценария
(`currentBlock>0`) — это могло пропустить очистку orphan-записей при
fork/replay в проде.

Корректный фикс: вернуть финальный `purgeAfterBlock(currentBlock)`
после `if`-блока (как было в оригинале) и устранить race c Initializer'ом
изящно — Initializer теперь принимает `block_num` параметром и не делает
свой собственный getInfo(). Reader передаёт ему тот же currentBlock,
что использует для финального purge; purge применяет $gt (а не $gte),
поэтому записи Initializer'а с block_num == currentBlock остаются.

Поведение всех трёх веток:
  • startBlock=1, currentBlock=0 (свежая БД): Initializer пишет
    с block_num=currentBlock; финальный purge оставляет его данные.
    Раньше Initializer писал с head_2 > head_1 и эти данные стирались.
  • startBlock=1, currentBlock>0 (прод hot-restart): Initializer не
    вызывается; финальный purge подчищает orphan-записи > currentBlock —
    идентично оригиналу.
  • startBlock!=1 (debug-replay): currentBlock = startBlock; финальный
    purge — идентично оригиналу.

Удалена локальная функция getInfo() в Initializer'е (больше не нужна).

Проверено: после restart на прод-сценарии (currentBlock=2077) deltas
для registrator/coops (3 записи) и soviet/boards (1) сохраняются;
Initializer корректно пропускается т.к. данные уже есть.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 13:28:21 +00:00
coopops 6743adf983 [350-1][@ant] feat(standards): 5 новых документ-стандартов + дораб p.cap.rid/invest/reg.accept
Новые стандарты (operations:[]):
- reg.coop — присоединение к платформе кооперативной экономики
  (regcoop+converttoaxn → 50+51 + операция o.sov.axncnv)
- sov.decision — принятие свободного решения советом (599+600)
- sov.selectbranch — прикрепление к кооперативному участку (101)
- meet.hold — проведение общего собрания (300/301/302/303/304)
- sov.authpkg — автоматизированное принятие решений советом
  (универсальный flow: newpackage → vote → authorize → exec → callback
   в инициатор; документ протокола 600)

Доработка существующих:
- p.cap.rid — добавлены actions pushrslt/approverslt/authrslt/declrslt;
  жизненный цикл расширен; проставлены registry_id 1040/1041/1042
- p.cap.invest — registry_id 1030 (CapitalizationMoneyInvestStatement)
- p.reg.accept — поле template: → registry_id: (100, 501)

UI: добавлен 'meet' → «Общие собрания» в CONTRACT_HUMAN.
2026-04-27 13:25:24 +00:00
coopops 3219459b8e [989-9][@ant] fix(parser,seed,docs): finalize results-сценарий — purgeAfterBlock до Initializer + 2 скриншота
Корневой блокер для seed-фаз через docs-harness:
  • parser/Reader: после reboot:extra Reader дёргал getInfo() и брал
    head_block_num как currentBlock; затем initializeFromBlockchain()
    делал getInfo() ВТОРОЙ раз и записывал deltas с block_num=head_2
    (head за это время мог шагнуть). Reader потом вызывал
    purgeAfterBlock(currentBlock=head_1), стирая все Initializer-данные
    с block_num > head_1 — Mongo оставалась пустой по cooperatives/boards,
    factory.Cooperative.getOne() падал «Совет кооператива не обнаружен»,
    seed-фаза 04 не могла зарегистрировать Contributor.
    Фикс: purgeAfterBlock ВЫЗЫВАЕТСЯ ДО initializeFromBlockchain. Теперь
    дельты Initializer'а попадают в Mongo и не стираются.

Заодно:
  • seed/13-push-result: voter-action data теперь содержит `username:
    voter` (а не остаточный `username: ant` из fakeVote). Без этого
    `has_auth(username)` в votefor.cpp возвращал true для ant, но false
    для остальных — контракт переходил к require_auth(coopname), а в
    authorization массиве coopname'а не было — «missing authority of voskhod».

  • docs-harness/scenarios/blagorost/results.mjs: убран дубликат-кадр
    `02-segment-actions` (UI этапа «Результат» — список карточек, не
    таблица; селектор tr:has-text не срабатывал). Остались два кадра:
    `01-overview` (страница «Результаты» с ColorCards и сегментами) и
    `02-convert-dialog` (диалог «Получить долю в ОАП» со слайдером).

  • docs/new/blagorost/results.md: вставлены image-references для обоих
    кадров; уточнены подписи под актуальный UI (вкладка «Результаты»,
    статус «Приёмка», читаемые названия пулов на ColorCards), добавлено
    пояснение «100% в Благорост» когда available_for_wallet=0.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 13:22:44 +00:00
coopops 448f580f45 [989-9][@ant] feat(seed-capital,docs-harness): сценарий results.mjs + фиксы фаз 07/13 для reboot:extra
Сценарий blagorost/results.mjs — три кадра пост-voting пути:
  • 01-overview — страница «Результат» (ColorCards + таблица сегментов);
  • 02-segment-actions — раскрытый сегмент пайщика с «Получить долю в ОАП»;
  • 03-convert-dialog — открытый ConvertSegmentDialog со слайдером
    «Главный Кошелёк ↔ Программа Благорост».
fixture lazily читается в default(), чтобы не падать на module-load
после reboot (когда фикстура ещё не создана orchestrator'ом). Указаны
`fixture: 'ivanpetrov'` + `fixtures: ['ivanpetrov', 'ekaterina']` —
обе нужны фазе 05.

Фаза 07 (master-and-plan):
  • input GetProjectWithRelations — `projectHash` (camelCase, без coopname)
    под актуальную schema контроллера.
  • Polling до 60с пока parser не индексирует createproject — иначе
    capitalSetPlan падает с «Проект ... не найден» сразу после фазы 06,
    у которой нет ожидания catch-up.

Фаза 13 (push-result):
  • processLastDecision теперь читает `soviet::boards` и голосует от
    каждого voting-члена совета (один WIF подписывает за всех — у всех
    общий default_public_key). Без этого после reboot:extra (5 членов
    совета) `soviet::authorize` падает с «Консенсус совета по решению
    не достигнут».

Известный блокер для скриншотов results — отдельная регрессия парсера:
после reboot:extra parser стартует с позднего блока (currentBlock~1070)
и пропускает createboard/regcoop, так что Mongo `cooperatives`
остаётся пустым; controller `Cooperative.getOne` падает «Совет кооператива
не обнаружен», и фаза 04 не может зарегистрировать contributor. Это не
проблема сценария, и фиксится отдельно — не моими правками.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 12:57:11 +00:00
coopops 4d567618a5 [989-9][@ant] feat(docs/blagorost): инструкция «Результат и получение доли»
Новая страница, описывающая весь пост-voting путь компонента:

  • Этап «Результат» — что появляется на странице, поля сегментов;
  • Пересчёт результатов — служебная кнопка обновления арифметики
    после закрытия голосования или изменения профиля пайщика;
  • Внесение результата мастером (хоткей R) — фиксация долей,
    обязательства паевого взноса РИДом, автоматический зачёт
    активных займов кооператива;
  • Признание совета — зачем нужен formal-flow председателя
    (confirmapprv → voteFor → authorize → exec);
  • Получение доли пайщиком — два акта (о результатах + приёма-
    передачи РИД), затем слайдер «Главный кошелёк / Благорост»
    как механизм конвертации направлений;
  • Удаление компонента после полной конвертации.

В `voting.md` добавлена сквозная ссылка на новую страницу: после
голосования читатель сразу понимает, куда переходит компонент
и какие действия его ждут как пайщика/мастера/председателя.

`mkdocs.yml` — новый пункт «Результат и получение доли» в разделе
«Благорост», расположен после «Голосования».

Скриншоты будут добавлены отдельным проходом docs-harness.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:54:21 +00:00
coopops 25064caabf [989-9][@ant] feat(docs/blagorost): инструкции «Коммиты» + «Голосование», правки «Инвестирование»
Две новые страницы документации компонента «Благорост»:
  • `commits.md` — пайщики добавляют коммиты в активный компонент через
    трекер, мастер одобряет; каждый одобренный коммит формирует РИД-обяз.
    на полную сумму на w.cap.gncom.
  • `voting.md` — переход компонента в голосование, как пайщики
    распределяют голоса по методу Водянова, расчёт voting_bonus и
    автоматическое закрытие.

В `investments.md` дочищена терминология: чёткое разделение «деньги»
vs «РИД» в путях паевого взноса.

Сценарии docs-harness под новые страницы:
  • `blagorost/commits.mjs`, `blagorost/voting.mjs` — съёмка серии
    скриншотов из desktop-кабинета пайщика и мастера.
  • `lib/harness.mjs`, `adaptation.mjs`, `investments.mjs`, `profile.mjs` —
    подкручены селекторы и шаги под текущий UI; снимки лежат в
    `assets/new/blagorost/{commits,voting}/`.

`mkdocs.yml` — добавлены два новых пункта nav в раздел «Благорост».

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:51:04 +00:00
coopops 37cbfb280e [989-9][@ant] feat(boot/seed-capital): фазы 09-14 — полный жизненный цикл компонента «Благорост»
Расширяем seed-сценарий за пределы инвестиций: компонент проходит
весь путь от задач до приёмки и конвертации направлений, чтобы
docs-harness снимал последовательные шоты для документации.

Новые фазы:
  09 — `tasks`        — четыре задачи мастер-плана с коэффициентами;
  10 — `commits-and-voting` — коммиты исполнителей + переход в голосование;
  11 — `cast-votes`   — равномерное распределение голосов всеми участниками
                        и автоматическое закрытие через cmpltvoting;
  12 — `recalc-and-calc-votes` — rfrshsegment + calcvotes по каждому;
  13 — `push-result`  — pushresult всеми пайщиками + soviet-цепочка
                        (confirmapprv → voteFor → authorize → exec)
                        + signact1/signact2 на каждый сегмент;
  14 — `convert-segments` — convertsegm с разной долей walletAmount/
                            capitalAmount по пайщикам; финализация
                            проекта.

Параметризация увеличена под более «сочный» демо-кейс:
  • hour_cost 1500 → 5000 RUB (07-master-and-plan)
  • размеры задач 8/6 → 30/20 часов (09)
  • коммит-часы 8/6 → 30/20 (10)
  • investAmount petrov 30K, ekaterina 10K (08)

`rotate-participant-keys.ts` — служебная утилита: после reboot:clean
WIF фикстур теряется; скрипт делает registrator::changekey + сохраняет
новый keypair, чтобы повторный seed работал поверх свежей цепочки.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:50:42 +00:00
coopops c33d5f8224 [989-9][@ant] test(capital): инвариант w.cap.gncom не уходит в дефицит после конвертации
После полного цикла commits→voting→pushresult→signact2→convertsegm для
комплексного компонент-проекта проверяем, что Σ COMMIT_RID(коммитов) >=
Σ ACCEPT_RID(сегментов): кошелёк w.cap.gncom (ЦПП «Генератор» — коммит)
по дельте проекта не уходит в минус.

Жёсткий инвариант — отсутствие дефицита (delta >= 0). Если он нарушен,
значит approvecmmt кладёт на w.cap.gncom меньше, чем signact2 забирает
у пайщиков — регрессия патча approvecmmt; в проде это «недостаточно
средств на кошельке GENERATOR_COMMIT» на signact2 последнего пайщика.

Эквивалентность delta == 0 не проверяется — investor3 идёт через
purgesegment без конвертации, тестеры с is_contributor=0 не получают
свою долю contributors_bonus, эта непокрытая часть остаётся как остаток
(в скрипте логирует ⚠️). Это допустимо для сложного сценария теста.

Дополнительно: sanity-чек на w.cap.bgrid (BLAGOROST_RID) — путь
ACCEPT_RID(w.cap.gncom → w.cap.bgrid) после signact2 хоть кого-то
перенёс средства.

Идентификаторы кошельков — eosio::name (рефакт 184530dab7). Старые
numeric ID 10001/9002 в коде не используются; wallets.id теперь string.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:50:20 +00:00
coopops 80807b2884 [989-9][@ant] fix(capital): approvecmmt кладёт на w.cap.gncom полную сумму коммита
Раньше approvecmmt после `Projects::add_commit` перечитывал segment и
эмитил COMMIT_RID на дельту `available_for_program` — это покрывало
только base/bonus создателя на момент коммита. Когда позже calcvotes
рассчитывал voting_bonus и докидывал `available_for_program`, signact2
последнего пайщика проекта забирал больше, чем лежало на w.cap.gncom
(GENERATOR_COMMIT) — walletop падал с «недостаточно средств».

Теперь COMMIT_RID эмитится на `commit.amounts.total_contribution` —
полную стоимость коммита (base+bonus всех ролей и contributors_bonus).
В сумме по всем коммитам проекта это ровно `project.fact.total_contribution`,
которое = Σ intellectual_cost всех сегментов; signact2 спокойно забирает
свою долю независимо от того, как голосование перераспределило бонусы.

Инвариант: Σ COMMIT_RID(коммитов проекта) == Σ ACCEPT_RID(сегментов).
GENERATOR_COMMIT (w.cap.gncom) закрывается в ноль на проекте, не на
конкретном сегменте.

Заодно убрана пост-modify выборка сегмента по `commit.project_hash` /
`commit.username` (secondary index по checksum256+name) — она давала
runtime «access violation» в WASM (multi_index secondary итераторы
становятся невалидными после modify; валится на eos-vm.cpp:165).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:50:07 +00:00
coopops 6ee88ff253 [989-9][@ant] docs(blagorost): убрать банковский лексикон — пайщик совершает паевой взнос
«Вкладывать»/«вложить»/«вклад» — банковская лексика, не для кооперативного
словаря. Пайщик не вкладывает — он совершает паевой взнос со счёта своего
цифрового кошелька. Кооператив принимает и возвращает паевые взносы.

Замены в страницах серии Благорост и в alt-описаниях сценария investments:
- «вложить паевой взнос» → «совершить паевой взнос»
- «вкладывает свои паевые взносы» → «совершает паевой взнос из собственных средств»
- «вкладывать паевые взносы» → «совершать паевые взносы»
- «вложить деньги» → «совершить паевой взнос»
- «не ваши вклады» → «не ваши взносы»

Затронуты: investments.md, master-and-plan.md, profile.md, project-create.md
+ description в scenarios/blagorost/investments.mjs.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:17:35 +00:00
coopops ad0c140255 [989-9][@ant] feat(blagorost): инструкция «Инвестирование» — два пути паевых взносов
seed-capital фаза 08-investments — программно подготавливает стенд для съёмки:
- soviet::sndagreement для petrov+ekaterina (соглашения wallet и blagorost
  ЦПП), создаёт пользовательские кошельки
- capital::getclearance + soviet::confirmapprv — приложения к УХД-договору
  для инвесторов
- capital::startproject + capital::openproject — компонент в active со
  включённым приёмом инвестиций
- wallet::createdeposit + gateway::completeincome — пополняет кошельки
  инвесторов (600 000 ₽ petrov, 300 000 ₽ ekaterina)
- capital::createinvest — petrov 500 000 ₽ → компонент MVP v1
- capital::createpinv  — ekaterina 200 000 ₽ → программа «Капитализация»

Сценарий blagorost/investments.mjs снимает 3 кадра:
- toggle «Принимает инвестиции» включён в sidebar (выделен)
- вкладка «План» компонента: строка «Привлекаемые инвестиции» в колонке
  «Факт» с реально поступившими средствами
- профиль с выделенной кнопкой «Инвестировать» под Кошельком Благороста

Проза investments.md описывает два пути инвестирования:
1) В компонент — пайщик сам приоритизирует, кнопка «Инвестировать (I)»
   на карточке компонента
2) В программу «Капитализация» — кнопка «Инвестировать» на профиле,
   совет распределяет средства между компонентами

Таблица сравнения двух путей; admonition про источник средств (основной
кошелёк) и про разделение паевых взносов пайщиков и финансирования
от кооператива.

mkdocs.yml: новая страница в разделе «Благорост» (Инвестирование).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:17:35 +00:00
coopops 75bd3a9fa1 [989-9][@ant] feat(blagorost): master-and-plan + аннотации/активация в project-create
master-and-plan:
- seed-capital фаза 07 — программно одобряет УХД-договоры всех contributors
  (soviet::confirmapprv через contributor_hash), подписывает приложение
  председателя к компоненту (capital::getclearance + confirmapprv), назначает
  мастера (capitalSetMaster) и устанавливает план 160 ч × 1500 ₽ + 50 000 ₽
  расходов (capitalSetPlan)
- сценарий blagorost/master-and-plan.mjs снимает 3 кадра:
  страница компонента с мастером, вкладка «План» компонента (таблица
  план/факт со всеми расчётными пулами от контракта), сводный план проекта
- проза master-and-plan.md описывает роль мастера, три значения плана
  (часы/ставка/доп.расходы), как контракт разворачивает их в полные пулы,
  что разблокирует переключатель «Принимает инвестиции»
- mkdocs.yml: новая страница в разделе «Благорост»

project-create:
- сценарий расширен: после Мастерской открывает карточку проекта (статус
  «Ожидает», sidebar выделен), переключает в «Активен» через UpdateStatus
  dropdown, переходит в карточку компонента и активирует её
- через lib/annotate.mjs накладывает красные рамки на ключевые элементы:
  «+ Проект (P)» в FAB, «+» в строке проекта, «Статус» в sidebar
- проза уточнена: Active разблокирует только приём коммитов; toggle
  «Принимает инвестиции» в sidebar — только после плана; в проекты
  напрямую не инвестируем

profile:
- второй кадр с прокруткой к таблице взносов
- проза описывает роли (Соавтор/Исполнитель/Инвестор/Координатор)
  и отдельно строку «Получено в Благорост» (доля от других пайщиков
  по правилам ЦПП)

infra:
- harness.mjs: shot() возвращает абсолютный path для пост-обработки PNG
  (annotate без сериализации в manifest)
- seed-capital/index.ts: phase 07 в реестре фаз

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:17:35 +00:00
coopops e8fe9247ff [989-9][@ant] fix(capital/desktop): watch projectStore.projects.items с {deep: true}
В ComponentPlanningPage и ProjectPlanningPage watcher на projects.items был без
{deep: true}, поэтому in-place мутации через splice (которыми store обновляет
items в loadProject/addProjectToList) не триггерили watcher. Локальный
project.value оставался stale, и ProjectPlanningWidget показывал «не установлено»
во всех ячейках таблицы план/факт даже когда is_planed=true и plan заполнен в БД.

В useProjectLoader (composables.ts) тот же watcher уже был с {deep: true} —
там UI обновлялся, в этих двух страницах было пропущено.

Дополнительно ComponentPlanningPage.loadProject теперь всегда форсит запрос
на сервер: раньше брал из store если уже там, что давало stale-значения,
загруженные до setMaster/setPlan.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:17:34 +00:00
coopops 184530dab7 [ledger2][@ant] refactor(ledger2): wallet IDs uint64_t → eosio::name
Сквозная замена числовых идентификаторов кошельков ledger2 (1001/2001/9001/...)
на eosio::name с префиксом w.<contract>.<waltype> по аналогии с операциями
(o.<contract>.<verb>) и процессами (p.<contract>.<noun>).

Маппинг:
  2001 → w.wal.share    (паевые деньгами)
  2002 → w.reg.minshr   (минимальный паевой)
  2003 → w.wal.sharid   (паевой фонд РИД)
  3001 → w.reg.entry    (вступительные)
  3002 → w.sov.member   (членские)
  3003 → w.sov.delgte   (делегатские)
  4001 → w.wal.wthdrw   (возвраты пайщикам)
  4002 → w.mkt.payout   (выплаты поставщикам)
  4051 → w.cap.loan     (займы)
  5001 → w.led.adjust   (ручные корректировки)
  9001 → w.cap.bginv    (Благорост — деньги)
  9002 → w.cap.bgrid    (Благорост — РИД)
  9003 → w.cap.bgprop   (Благорост — имущество)
  9004 → w.cap.bgmem    (Благорост — членские)
  10001 → w.cap.gncom   (Генератор — коммит)
  10002 → w.cap.gnmem   (Генератор — членские)
  11001 → w.mkt.fund    (Стол Заказов)
  0     → eosio::name{} (sentinel «вне системы» для ISSUE/REVOKE)

Затронуто:
  • C++ контракты: wallets.hpp, operations.hpp, table_ledger2_wallet.hpp
    (id: uint64_t → eosio::name, primary_key() = id.value), actions
    walletop/walmove/revert.
  • cooptypes: WalletMeta { name: IName, human_name }, OperationMeta
    wallet_from/to: IName | null, IWallet2.id, IWalmove, IRevert.
  • controller: DTO Int → String, getLedger2History разделён на accountId
    (число) + walletName (строка), repository без ::bigint для wallet полей.
  • SDK zeus/index.ts: 4 секции типов под String + walletName поле.
  • desktop: WalletIdCell prop wallet-name, store getWalletByName, query
    param wallet_name=, OperationsPage filter walletName.
  • YAML стандарты: 10 файлов processes capital/marketplace/registrator/
    soviet/wallet — wallet_from/wallet_to ('' для sentinel).
  • boot tests: walmove/migrate/read-layer на eosio::name.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 11:11:46 +00:00
Alex Ant cca16d6d3e chore(release): publish 2026-04-27 11:59:09 +05:00
Alex Ant e4701d1b2e Merge branch 'testnet' 2026-04-27 11:58:56 +05:00
Alex Ant 443b11480d chore(release): publish 2026-04-27 11:23:16 +05:00
coopops 77734368b9 [350-1][@ant] feat(standards-site): итерация UX — урезанный реестр, человеческие подписи контрактов, единый стиль названий
YAML-стандарты:
  • удалены p.cap.import («Импорт пайщика», частный кейс ВОСХОДа) и
    p.sov.axncnv («Конвертация паевого в делегатский ЧВ», частный кейс
    инфраструктуры) — оба не относятся к общему реестру кооперативных
    стандартов; ссылки на них вычищены из p.reg.accept, p.cap.invest,
    p.mkt.reqst.
  • унифицированы названия в стиле «глагол-существительное действия»:
      p.cap.debt    «Займ пайщику» → «Выдача займа пайщику»
      p.cap.invest  «Инвестиция в программу» → «Приём инвестиции в программу»
      p.mkt.reqst   «Запрос маркетплейса» → «Исполнение заказа на поставку имущества»
  • в p.reg.accept откачена попытка добавить альтернативный путь через
    registrator::adduser — визуально длинная стрелка bypass'а пересекала
    main-flow, уверенно расположить её в графе не получилось; в реестре
    остаётся одно «Приём пайщика» с одним основным сценарием.

UI standards-site:
  • новый файл src/data/labels.ts — общие словари CONTRACT_HUMAN
    (registrator → Регистратор, wallet → Главный кошелёк, capital →
    «Благорост», marketplace → «Стол заказов», soviet → Совет,
    ledger2 → Учёт операций) и STATUS_HUMAN (proposed → предложен,
    approved → утверждён, active → действующий, deprecated → устаревший).
  • Sidebar и HomePage показывают группы как «русское имя + мелкий
    code-бейдж с английским» вместо ведущего ALL-CAPS-тех-имени —
    русский становится первичным, тех-код вторичным.
  • На главной убраны (1) упоминание ledger2 и process_type из
    интро-абзаца, (2) тикер «одноактовый / N операций» с карточек,
    (3) дублирующий <code>process_type</code> под названием стандарта;
    статус выводится по-русски через statusHuman.
  • layout.ts очищен от alt-bypass-логики (rerouted target=END_ID +
    post-layout y/x reposition) — она была нужна только под adduser.

Зачем: реестр должен показывать председателю общие кооперативные
стандарты на понятном языке, а не технические артикулы с английскими
кодами. ВОСХОД-специфика и внутренние ledger2-механики из реестра
вычищены — они остаются в C++ контрактах и cooptypes-реестрах, но
не претендуют на статус общекооперативного стандарта.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-27 06:10:11 +00:00
coopops f51bbf32b0 [989-9][@ant] chore(docs): убрать «Реестр стандартов» из главного меню
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 17:40:59 +00:00
coopops d3cc96fcd5 [989-9][@ant] feat(blagorost): seed-capital фазы + 4 страницы документации
seed-capital — поэтапная подготовка стенда для doc-shoot. Диспетчер принимает
список фаз и --up-to=<phase> — стенд можно остановить в любой точке для ручного
теста UI на конкретном этапе.

Фазы:
- 01-programs / 02-extension-config / 03-projects (реестр из _blago/INDEX.md + Кошелёк пайщика)
- 04-contributor (председатель ant) / 05-additional-contributors (ivanpetrov, ekaterina)
- 06-create-project-koshelek (рабочий проект для серии «Генерация»)

Сценарии и документация (components/docs/docs/new/blagorost/):
- adaptation, profile, projects-list, project-create

Orchestrator bin/shoot.mjs: поддержка meta.fixtures (явный список пайщиков для
seed-фаз) + meta.prepare (запуск нужных фаз перед сценарием).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 17:40:59 +00:00
coopops c739743c4b [350-1][@ant] feat(standards): альтернативный путь приёма (adduser) + акты приёма-передачи + убрать ledger2-стандарт
p.reg.accept — добавлен альтернативный однокликовый путь приёма пайщика:
  • action registrator::adduser (actor: председатель), role: closer
  • transition ∅ → active напрямую, минуя created/payed
  • триггерит o.reg.putmin (всегда) и опционально o.reg.payent
    (если spread_initial=true)
  Это путь для исторических участников и случаев, когда заявление и
  решение совета оформлены офлайн-документами; председатель добавляет
  пайщика как сразу активного. Под капотом тот же процесс p.reg.accept,
  но с другой вилкой на старте.

p.cap.rid — title в Sidebar изменён с «Приём результатов интеллектуальной
деятельности» на «Приём результата интеллектуальной деятельности»
(единственное число) + переименование «акт-1»/«акт-2» в человеческий
язык: «акт приёма-передачи РИД» — один документ с двумя подписями
(первая подпись участника, вторая — председателя).

p.cap.prop — аналогичная семантика акта приёма-передачи имущества: один
документ, две подписи (пайщик первый, председатель второй). Действия,
статусы и тексты сценария переписаны с «акт-1/акт-2» на «первая/вторая
подпись на акте приёма-передачи».

p.cap.debt — упоминания «акт-2 проекта» в описании o.cap.repay заменены
на «акт приёма-передачи проекта».

p.adj.fix — стандарт удалён целиком. Контракт ledger2 описывает
кооперативный учёт операций, а не сами кооперативные операции; ручная
корректировка председателя — внутренний механизм исправления учёта,
а не пользовательский on-chain процесс кооператива. В реестре стандартов
ему делать нечего.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 17:11:18 +00:00
coopops 0cb8197cab [@ant] fix(desktop/capital): таблица участников зависала на 10 записях из-за неправильного ключа
GraphQL-запрос capitalContributors ожидает аргумент options (PaginationInput),
а фронт передавал pagination — неправильный ключ молча пропускался через
индекс-сигнатуру `[key: string]: unknown` в SDK-типе IInput, и backend каждый
раз применял дефолт limit=10. Поэтому q-pagination показывал максимум 1 страницу.

- ContributorsPage.vue: pagination → options в loadContributors и reloadContributors,
  descending: boolean → sortOrder: 'ASC'|'DESC'.
- useContributorSearch.ts: pagination → options в loadContributors и preloadContributors,
  descending → sortOrder.

Теперь rowsPerPage=25 со страницы реально доходит до бэка, totalCount возвращает
полное число участников и q-pagination показывает все страницы.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 16:48:33 +00:00
coopops ca332f1078 [350-1][@ant] fix(standards-site/nodes): увеличить статус- и action-узлы и разрешить перенос названия на 2 строки
State: 180×80 → 220×96, action: 170×54 → 210×68 (плюс синхронизирован
SIZE в graph/layout.ts, чтобы dagre не оставлял nodes налезающими).

Названия (.node-state__human / .node-action__human) — переход с
white-space: nowrap + ellipsis на line-clamp:2 (display: -webkit-box,
-webkit-line-clamp: 2, word-break: break-word). Длинные русские
заголовки вроде «Получение подтверждено», «Решение совета подписано»,
«Авторизовать выплату», «Подтвердить выплату» теперь помещаются
полностью без обрезания троеточием.

Зачем: после реальной заливки 11 стандартов выяснилось, что русские
названия статусов и действий часто длиннее английских артикулов —
дефолтные размеры узлов «съедали» половину текста. Председатель
смотрел на «Получение подтв…» и не понимал, чем оно отличается от
«Получение». Теперь видно полностью.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 11:58:21 +00:00
coopops 56d10d10c9 [350-1][@ant] fix(standards-site): зафиксировать ThemeToggle снизу + почистить названия в Sidebar и YAML
Sidebar.vue:
  • .sidebar-body теперь со своим overflow-y: auto (раньше скроллился весь
    sidebar и foot уезжал вверх вместе со списком).
  • .sidebar-foot — flex: 0 0 auto, чтобы кнопка темы держалась внизу даже
    при длинном списке.
  • Убрана подпись с process_type под названием стандарта в списке —
    идентификаторы вроде «p.cap.invest» в навигации не нужны, они
    видны в URL и на странице процесса.

Названия стандартов (top-level title в YAML):
  • p.cap.import   «Импорт пайщика «Благорост» (offline)» → «Импорт пайщика»
  • p.cap.invest   «Инвестиция в ЦПП «Благорост»» → «Инвестиция в программу»
  • p.cap.rid      «Приём РИД в паевой фонд» → «Приём результатов
                    интеллектуальной деятельности»

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

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 09:35:22 +00:00
coopops 3cb3b0cf9b [350-1][@ant] feat(standards): черновики 9 стандартов из реестра процессов — wallet/withdraw, capital, marketplace, soviet, ledger2/adjust
Покрыты все процессы LEDGER2_PROCESS_REGISTRY кроме p.mig.trans
(одноразовая миграция legacy → ledger2, не нужна как стандарт):

  • p.wal.wthdrw   — Возврат паевого взноса (5 actions, 2 docs, 1 op)
  • p.cap.import   — Импорт пайщика «Благорост» offline (1 action, 0 docs, 1 op)
  • p.cap.invest   — Инвестиция в «Благорост» (1 action, 1 doc, 1 op WALLET_ONLY)
  • p.cap.debt     — Беспроцентный заём пайщику (6 actions, 3 docs, 2 ops)
  • p.cap.rid      — Приём РИД в паевой фонд (6 actions, 3 docs, 3 ops)
  • p.cap.prop     — Имущественный паевой взнос (6 actions, 4 docs, 1 op)
  • p.mkt.reqst    — Запрос маркетплейса (12 actions, 10 docs, 2 ops)
  • p.sov.axncnv   — Конвертация паевого в делегатский ЧВ (1 action, 1 doc, 1 op)
  • p.adj.fix      — Ручная корректировка председателя (2 actions adjustment-kind, 0 docs, 2 ops)

Зачем: реестр кооперативных стандартов v1 должен покрывать каждый
on-chain процесс из контрактного LEDGER2_PROCESS_REGISTRY — это та самая
карта значимых пользовательских сценариев кооператива, которую видит
председатель. Без черновиков по 9 процессам сайт показывал только 2
пилотных стандарта; теперь у каждого процесса есть YAML-описание со
всеми секциями (паспорт, действия, граф состояний, сценарий, документы,
операции, связи), и любая последующая правка идёт точечно.

Все коды (process_type, ledger_code, wallet_to/from, debit/credit) сверены
с актуальными реестрами в components/cooptypes/src/ledger2/{processes,
operations,wallets,accounts}.ts. Список действий и статусов извлечён из
C++-контрактов (cpp/<contract>/<contract>.hpp + src/). Где документы
имеют известный registry_id (p.sov.axncnv → 51 ConvertToAxonStatement) —
проставлен; для остальных registry_id:0 + TODO для последующей сверки
по cooptypes/cooperative/registry/.

p.mig.trans пропущен по решению: миграция — одноразовый административный
процесс без пользовательского сценария, не относится к набору
стандартов кооператива.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 09:25:06 +00:00
Alex Ant eb6ca73fb3 Merge pull request #363 from coopenomics/release/v2026.4.26-4
release: v2026.4.26-4 (production)
2026-04-26 14:20:48 +05:00
coopops 9a983e67fe chore(release): publish 2026-04-26 09:20:14 +00:00
coopops 3f4a2c006e Merge branch 'testnet' 2026-04-26 09:19:54 +00:00
coopops 151610ac38 chore(release): publish 2026-04-26 09:19:42 +00:00
coopops 12f5fa38d4 [@ant] fix(capital): отфильтровывать задачные stories на проекте/компоненте
Story-репозиторий findAllByProjectHashesAndIssueHashes делает выборку как
`project_hash IN (...) OR issue_hash IN (...)`. Story, привязанная к задаче,
всё равно имеет project_hash родителя задачи и попадала в результат через
первое условие — даже когда мы сознательно передавали пустой массив issueHashes
(показ задачных требований выключен).

Фикс: пост-фильтр в getStories — при `showIssuesRequirements=false`
выкидываем stories с непустым `issue_hash`. Теперь страницы проекта/компонента
показывают только проектные/компонентные требования, а задачные требования
доступны только через `filter.issue_hash` (страница задачи).

Дефолт `show_issues_requirements=false` (в DTO и сервисе) оставлен — теперь
он действительно работает, а не «делает вид».

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 09:17:08 +00:00
coopops d0ff0df649 [@ant] fix(ci/publish-packages): pnpm 8.15.8 → 10.33.0 под lockfile v9.0
CI workflow «Publish Packages» падал на `pnpm install --frozen-lockfile`:
старая pnpm 8 не понимает lockfileVersion 9.0 (lockfile сгенерён локально
pnpm 10.33.0). На последнем production-релизе из-за этого failed check
заблокировал автомерж в main; merge пришлось делать с --admin override,
а сама публикация npm-пакетов из CI не выполнилась.

Прибиваем версию pnpm в action-setup к 10.33.0 — той же, что у user'а
локально. Комментарий обновлён: lockfileVersion 9.0 = pnpm 9/10
(старый комментарий говорил про 6.0/pnpm 8 — это уже не актуально).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 09:03:24 +00:00
Alex Ant ee5df670ca Merge pull request #362 from coopenomics/release/v2026.4.26-2
release: v2026.4.26-2 (production)
2026-04-26 14:00:57 +05:00
coopops 686d33ca53 [350-1][@ant] feat(standards-site): подтянуть актуальный UI из dev — links-кнопки, документы у действия, поддержка slim+legacy
Подтянуты три файла из dev: FocusBar.vue, graph/layout.ts, types/standard.ts.
Изменения обратно-совместимы — types и layout одновременно понимают и
reports-схему (scenario.steps + doc.template + doc.step + actions[].role),
и slim-вариант из dev (doc.action + doc.registry_id + actions[].links[]).

Зачем: ветка standards/reports = origin/reports + актуальный UI; YAML-файлы
reports (p.reg.accept, p.wal.depo) рендерятся как раньше, а будущие правки
по стандартам поверх reports получают новые UI-возможности (кнопки-переходы
между стандартами, отдельная колонка «Документы» рядом с действием,
читаемый код документа с приоритетом registry_id над template).

Источник правды по схеме — reports; slim-формат остаётся в dev до
момента, когда reports пойдёт первой в мердж и подомнёт устаревшие
slim-YAML (reg.regist/reg.adduser/reg.recovery/wall.deposit) — это
будет отдельный pre-merge cleanup в dev.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 08:52:20 +00:00
coopops eaf63ed375 chore(release): publish 2026-04-26 08:51:05 +00:00
coopops 23adebc281 chore(release): publish 2026-04-26 08:39:02 +00:00
coopops 67306c2637 [989-9][@ant] refactor(docs-harness): перенести в components/docs-harness/
Корневая папка docs-harness/ выглядела чужеродно — все остальные TS/JS-инструменты в репо живут как workspace-пакеты в components/. Перенёс рядом с components/docs/ — есть прямая логическая связь (один производит контент, второй публикует).

- `git mv docs-harness components/docs-harness` — workspace автоматически подхватит, в pnpm-workspace.yaml и lerna.json не трогаем (там уже `components/*`).
- package.json: name `browser-harness` → `@coopenomics/docs-harness`, добавлен `"private": true` (никогда не публиковать), `"type": "module"`, скрипт `pnpm shoot` как алиас orchestrator'у.
- bin/shoot.mjs: REPO_ROOT теперь поднимается на 2 уровня (`HARNESS_ROOT/../..`), не на 1. Финальный вывод печатает относительные пути от корня репо.
- lib/install.mjs: DEFAULT_DOCS_ROOT теперь `HARNESS_ROOT/../docs/docs` (соседний components/docs/docs/), не `../components/docs/docs/`.
- Пути в SKILL.md обновлены (`docs-harness/` → `components/docs-harness/`).

Smoke-тест: `cd components/docs-harness && node bin/shoot.mjs auth/signin` проходит за ~30с — стек/dist/desktop/фикстура/прогон/render все ок, 3 шота снимаются.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 08:33:28 +00:00
coopops 620d4f149b [@ant] feat(desktop/capital): на странице задачи виджет «Требования к задаче»
Под описанием задачи добавлен expansion-item «Требования к задаче»
с переиспользованным RequirementsListWidget (фильтр {issue_hash}) и
кнопкой «Добавить требование», открывающей CreateRequirementWithEditorDialog
(prefill {project_hash, issue_hash} → backend создаёт story с issue_hash).

- IssuePage.vue: новая секция в обоих layout (mobile/desktop), счётчик в caption,
  использует issue.permissions.can_create_requirement.
- RequirementsListWidget.vue: prop permissions расширен union'ом
  IProjectPermissions | IIssuePermissions — поля can_edit_requirement /
  can_delete_requirement совпадают по форме, виджет не отличает.
- CreateRequirementFabAction.vue, CreateRequirementWithEditorDialog.vue:
  filter принимает issue_hash (не только legacy issue_id).

Серверная логика: GetStories по project_hash дефолтно НЕ возвращает stories
с issue_hash (см. предыдущий коммит 89c28b89c1 в controller), поэтому
такие требования видны только на странице задачи и не аккумулируются
на проект/компонент. Matrix-нотификации для них тоже отключены.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 08:29:48 +00:00
coopops 89c28b89c1 [@ant] feat(capital,blago-cli): требования к задаче изолируются от проекта/компонента
Требования (story) с issue_hash перестают аккумулироваться на странице проекта/
компонента и не публикуются в matrix-комнаты — они живут только на странице
самой задачи (DC-фронт добавит виджет следующим коммитом).

- controller/StoryFilterInputDTO.show_issues_requirements: defaultValue true → false
  (комментарий: задачные требования не нужны на проекте/компоненте). Фронт-страницы
  ProjectRequirementsPage и ComponentRequirementsPage уже передают false явно,
  так что новых правок там не требуется.
- controller/generation.service.getStories: дефолт показа issue-stories синхронизирован
  с DTO (`=== true` вместо `!== false`).
- controller/generation.service.publishNewStoryToProjectMatrixChats: ранний return,
  если у story задан issue_hash — нотификация в проектную matrix-комнату не идёт.
  Существующие refs в matrix_requirement_announcement_events продолжают работать
  через sync/remove (если кто-то уже публиковал до этого фикса).
- blago-cli/layout.ts: stories с issue_hash раскладываются под
  `<base>/issue-requirements/<task-id>-<task-slug>/<story>.md` (отдельная папка
  верхнего уровня, чтобы локально не засорять `requirements/` контекст
  компонента/проекта).
- blago-cli/run-create-story.ts: фолбэк имени файла под новой схемой.

Миграция: следующий `blago pull` сам перенесёт существующие файлы и подчистит
пустые родители (см. ранее добавленный pruneEmptyParents в sync-entity-file.ts).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 08:25:15 +00:00
coopops 109f02f894 [989-9][@ant] feat(docs-harness): orchestrator поднимает docker compose сам + флаг --reboot
Раньше orchestrator делал fail-fast если chain/controller/parser лежали — пользователь должен был вручную поднимать стек. Теперь:

- Сервис лежит → `docker compose up -d <name>` + ожидание (60-120с по типу). Если после поднятия всё равно не отвечает — fail с пояснением.
- `node bin/shoot.mjs <scenario> --reboot` → перед всем остальным вызывает `pnpm run reboot:extra` (полный снос blockchain-data + volumes + boot:extra) и удаляет все фикстуры из state/participants/, потому что их WIF на новой цепочке невалидны. Дальше ensureFixture() пересоздаёт пайщика заново.

Использовать --reboot когда сценарий нужен «с нуля» или цепочка/БД разъехались с состоянием. Полный цикл ~3-5 мин.

Разрешения зафиксированы в memory `feedback_infra_permissions.md` (и обновлён SKILL.md): в этом репо я могу самостоятельно `docker compose up -d` и `pnpm run reboot:extra`, пользователь руками не делает.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 08:24:18 +00:00
coopops 3e4d0632f8 [989-9][@ant] feat(docs-harness): bin/shoot.mjs orchestrator + актуализировать install.mjs
Один вход для doc-shoot скилла — `node bin/shoot.mjs <scenario>` сам делает pre-flight и автопочинку типовых грабель, чтобы прогон шёл без ручной возни:

- chain/controller/parser — fail-fast с подсказкой docker compose, если что-то лежит
- cooptypes/sdk dist — без них desktop отдаёт пустой спиннер; orchestrator билдит `pnpm --filter ... build`
- desktop dev :2999 — поднимает в фоне если не запущен; рестартует если только что собрали dist (vite-plugin-checker иначе держит кэш «no module» и vue-tsc overlay перехватывает клики Playwright)
- фикстура пайщика — парсит сценарий на ссылку state/participants/<name>.json; если файла нет, лезет в KNOWN_FIXTURES (внутри shoot.mjs) и создаёт через add-plain-participant.ts; неизвестный username → fail с подсказкой добавить профиль
- run.mjs + render-md.mjs (если draft нет)

Намеренно НЕ делает: не поднимает docker, не пишет прозу в draft.md, не вызывает install.mjs (запись в components/docs/ остаётся под ручным контролем).

install.mjs:1 — поправил устаревший комментарий про /home/admin/mono-ai-2 (фактический дефолт давно относительный — соседняя components/docs/docs/ от harness).

SKILL.md в ~/.claude/skills/doc-shoot/ обновлён отдельно (вне репо): убран mono-ai-2, поправлено что signin это пайщик а не председатель, основной поток теперь через bin/shoot.mjs.

Проверено: orchestrator проходит на текущем сценарии auth/signin за ~30с, все 3 скриншота снимаются, draft.md генерируется.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 08:17:51 +00:00
coopops 5728d0a01e [@ant] feat(blago-cli): требования к задачам — путь requirements/<task>/<story>.md
Stories с issue_hash раскладываются под `<base>/requirements/<task-prefix>-<task-slug>/`
(вместо прежнего `<base>/issues/.../...-requirements/`). Так все требования —
и привязанные к компоненту/проекту, и привязанные к задаче — сидят в одной папке
`requirements/`, а `issues/` хранит только файлы задач.

- layout.ts: новый путь для stories с issue_hash.
- run-create-story.ts: фолбэк имени файла под новой схемой.
- sync-entity-file.ts: после rename подчищаем пустые родительские каталоги,
  чтобы старые `<base>/issues/<task>-requirements/` не оставались артефактом.
- workspace-index.ts: для stories с issue_hash в INDEX.md выводим
  «(задача <id> в <компонент>)» вместо «(проект/компонент <id>)»; задачи
  попадают в карту id ровно для этой подписи (в самом INDEX.md задач нет).

Ручной миграции не требуется: на ближайшем `blago pull` syncEntityFile увидит
новый канонический путь и переместит файл, зачистив пустую старую папку.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 08:11:10 +00:00
coopops 7f3a26f268 [989-9][@ant] feat(docs-harness): принести harness + signin-инструкцию из ветки 989-4 поверх актуального reports
Без merge'а старой ветки 989-4 (там 47/48 коммитов — устаревшие версии ledger2/reports работы, уже сделанной заново в 989-1/2/3 и доехавшей до reports). Принесена только инфраструктура для съёмки документации:

- docs-harness/ — playwright-сценарии + хелперы (lib/{harness,annotate,install,render-md}.mjs), run.mjs, package.json, README, scenarios/auth/signin.mjs
- components/boot/src/scripts/add-plain-participant.ts — генератор фикстур пайщиков для harness
- components/docs/docs/new/auth/signin.md + 3 PNG в assets/new/auth/signin/ — эталонная инструкция «Вход пайщика»
- components/docs/mkdocs.yml — добавлена секция «Вход в систему» в nav (без удаления ссылки «Реестр стандартов» — это посторонний шум 989-4)

Проверено: npm install проходит, синтаксис всех .mjs чистый, run.mjs стартует и доходит до загрузки сценария — дальше нужны живые chain/parser/controller/desktop и фикстура ivanpetrov (генерируется add-plain-participant).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 06:33:25 +00:00
coopops 044d291731 [@ant] feat(blago-cli): убрать задачи из INDEX.md
Раздел «Задачи» создавал слишком много шума — задачи обычно ищут с привязкой к
проекту/компоненту, а сам проект/компонент находится по этому индексу. Оставлены
проекты, компоненты и требования.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 06:16:29 +00:00
coopops 3e845c226f [@ant] feat(blago-cli): освежать индекс родителя после create/del и автогенерировать INDEX.md
Чтобы безопасный паттерн (создание/удаление дочерней issue/story) работал из коробки:
- runCreateIssue, runCreateStory, runDelete после успешной мутации запрашивают GetProject
  и через refreshParentProjectVersion обновляют remote_updated_at родителя в index.json
  (если файл «грязный» — только индекс, иначе ещё и переписывают файл свежим контентом).
  Если на сервере между нашими операциями содержимое реально менялось извне — индекс не
  трогаем, чтобы push выявил настоящий конфликт.

- При pull/push/create/del/restore/clean генерируется корневой INDEX.md рабочей копии
  с проектами, компонентами, требованиями и задачами и относительными путями — для
  быстрой адресации без обхода дерева. Полные UUID требований сокращаются до 8 символов.
  INDEX.md добавлен в .blagoignore по умолчанию.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-26 06:16:29 +00:00
coopops 6ff97a3ff4 [989-9][@ant] fix(reports): даты как обычные инпуты + календарь по клику на иконку
Поля «С даты» / «По дату» больше не readonly — можно ввести 2026-04-01 руками.
mask `####-##-##` оставлен для формата. reload запускается только при полной
дате (10 символов), чтобы не мигать индикатором загрузки на каждой цифре.
Иконка event как и раньше открывает q-popup-proxy с q-date.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-25 16:07:09 +00:00
coopops 459262739e Revert "[989-9][@ant] fix(reports): «процесс» → «операция» в UI рабочего стола"
This reverts commit ad6559b98f.
2026-04-25 15:54:48 +00:00
coopops ad6559b98f [989-9][@ant] fix(reports): «процесс» → «операция» в UI рабочего стола
Пользовательские лейблы переименованы для консистентности с реестром
(там карточки уже называются «Операция …»):
- placeholder поиска: «ID процесса» → «ID операции»
- развёрнутая запись: «Тип процесса:» → «Тип операции:», «ID процесса:» → «ID операции:»

`process_hash` как машинный идентификатор (URL query, action data) не трогаем —
это контрактный термин.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-25 15:51:12 +00:00
coopops b60580f406 [989-9][@ant] feat(reports): revert → contract-only (whitelist auth, без UI/backend mutation)
Председатель больше не может откатывать операцию через UI: action `ledger2::revert`
сохранён, но принимает только подпись от whitelisted-контрактов
(`check_auth_and_get_payer_or_fail(contracts_whitelist)` без ветки `has_auth(coopname)`).

Why: ledger2 — учётный слой; зеркальная проводка председателем top-level
рассинхронизирует state контрактов-инициаторов (registrator/wallet/capital).
Контракты-инициаторы знают свой operation_code и могут собрать корректные
параметры зеркала из cooptypes/operations.hpp; они же одновременно откатывают
свои домены (participants/deposits/contributors).

Контракт ledger2:
- revert.cpp: убрана ветка has_auth(coopname); top-level от пайщика/председателя
  падает на whitelist-check. Все остальные проверки (запрет o.mig.*, валидация
  mirror-параметров) сохранены.

Backend (controller):
- удалены: revertOperation mutation, RevertOperationInputDTO, метод service
  revertOperation + computeMirrorParams + WALLET_OP_CODE map, RevertBlockchainDomainInterface
  и адаптер revert(), Ledger2StatePort.getOperationByGlobalSequence + repo-метод
- осталось: walmove (с UI), порт revert на cooptypes для контрактных потребителей

SDK:
- удалена mutation/ledger2/revertOperation.ts; cooptypes Actions.Revert + IRevert
  оставлены (нужны другим контрактам).

UI (desktop):
- удалён RevertOperationDialog.vue
- из OperationsPage убраны: import RevertOperationDialog, useSession/storeToRefs,
  revertDialog state, canRevert/openRevertFor/onRevertSuccess, кнопка ↩
- Ledger2 store/api/types: убран revertOperation method/IRevertOperationInput

Тесты:
- удалены revert.test.ts + adjust/revert.ts helper
- walmove.test.ts (3 теста) + остальной suite — зелёный

Полный suite: 92 passed | 1 skipped | 0 failed (clean reboot).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-25 15:30:11 +00:00
coopops 17d44ab152 [989-9][@ant] fix(reports): убрать hint у поиска process_hash — ломал визуал шапки фильтров
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-25 14:51:40 +00:00
coopops 3d7d9a8905 [989-9][@ant] fix(reports): корректировки в общем списке + поиск process_hash + закрытие диалогов
OperationsPage:
- по умолчанию actionNames=[apply,walmove,revert] (раньше только apply,
  и корректировки появлялись только с включённым «Только корректировки»)
- поле «ID процесса (process_hash)» в шапке фильтров: Enter / клик-иконка
  применяет точный hash (lower-case), очистка сбрасывает фильтр
- processHashInput синхронизируется с route.query.process_hash при mount

WalletTransferDialog / RevertOperationDialog:
- закрытие после успеха через прямой emit('update:modelValue', false)
  до finally — раньше close() блокировал guard'ом на loading=true,
  поэтому диалог не закрывался после успешной транзакции
- SuccessAlert больше не показывает кусочек process_hash (его всегда
  можно посмотреть в реестре через новый поиск)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-25 14:42:32 +00:00
coopops 70da6fd06f [989-9][@ant] fix(reports): WalletTransferDialog в правильное место pug-template
Случайно вставил Dialog внутрь q-table body, разорвав expanded q-tr
(`Inconsistent indentation. Expecting either 2 or 8 spaces/tabs` на
template(#item)). Перенёс на уровень div.page-shell — рядом с q-card.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-25 10:54:20 +00:00
coopops d340eed56c [989-9][@ant] feat(reports): корректировки председателя — walmove + revert (Sprint 5 Epic 5 MVP)
Контрактный слой ledger2:
- new actions ledger2::walmove (operation o.adj.walmove) — перевод между
  кошельками одного бух.счёта без Dr/Cr; ledger2::revert (operation o.adj.rev)
  — зеркальная проводка по originalGlobalSequence; запрет revert на o.mig.*
- new WalletOp::REVOKE для зеркала ISSUE (изъятие с wallet_from без to)
- namespace operations::adjustment (WALMOVE/REVERSAL) + processes::adjustment::CORRECTION
- OPERATION_ADJUSTMENT_REGISTRY — отдельный мини-реестр для UI human_name
  (динамические параметры не входят в OPERATION_REGISTRY)

cooptypes (зеркало контракта):
- WalletOp += 'REVOKE'; LEDGER2_OPERATION_REGISTRY += 2 adjustment-записи (kind:'adjustment')
- LEDGER2_PROCESS_REGISTRY += p.adj.fix
- new actions/walmove.ts + actions/revert.ts + IWalmove/IRevert интерфейсы
- helper isAdjustmentOperation(code)

controller (backend):
- Ledger2BlockchainPort + Ledger2BlockchainAdapter — подпись coopname@active
- DTO WalmoveInputDTO / RevertOperationInputDTO / Ledger2AdjustmentResultDTO
- Ledger2Resolver mutations walmoveWallets / revertOperation (роль chairman)
- Ledger2Service: walmove валидирует одинаковость account_id источника и
  получателя через cooptypes; revertOperation поднимает оригинал из
  blockchain_actions, swap Dr/Cr и ISSUE → REVOKE для зеркала
- TypeOrmLedger2StateRepository.getOperationByGlobalSequence
- process-hash-locator: + p.adj.fix → []

SDK (regen + новые мутации):
- mutations/ledger2/walmoveWallets.ts + revertOperation.ts
- selectors/ledger2/ledger2AdjustmentResultSelector.ts
- Zeus regenerated

UI (рабочий стол reports):
- WalletTransferDialog: select from/to (фильтр по тому же account_id),
  amount, обязательное memo; иконка ↔ в строке кошелька + кнопка «Перевести»
  в шапке (только председателю) → CoopWalletsPage
- RevertOperationDialog: превью операции, обязательное memo, баннер для o.mig.*;
  кнопка «↩ Откатить» в шапке развёрнутой записи OperationsPage
- Toggle «Только корректировки» в фильтрах OperationsPage (actionNames=walmove,revert)
- Ledger2 store/api: methods walmoveWallets / revertOperation; types

Тесты (89/90 → 94/95 passed | 1 skipped | 0 failed):
- walmove.test.ts: успешный перевод 2002→2001 + проверка accountBalance
  не меняется (WALLET_ONLY) + запрет на разные счета + запрет пустого memo
- revert.test.ts: откат o.reg.putmin восстанавливает 2002 и счёт 80 +
  запрет revert миграционных операций
- balance читается напрямую с чейна (parser отстаёт на минуты после reboot)

Документация:
- epic-5: декомпозиция на WalMove ✓ / Reversal ✓ / Manual ⏸
- adr-manual-corrections.md: почему Manual отложен (нужен документ
  протокола решения совета — XSD/шаблон/registry/processDecision-flow)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-25 09:04:37 +00:00
coopops cca8781168 [989-9][@ant] test(boot): починить оставшиеся 4 pre-existing failure'а + регенерация sdk zeus
Все 90 тестов теперь зелёные (89 passed | 1 skipped | 0 failed).

Изменения:

* boot/src/init/infra.ts: 2s → 8s sleep между setContract и createToken.
  На свежем nodeos setabi последнего контракта не успевал коммититься,
  eosjs.getAbi('eosio.token') падал с "Read past end of buffer".

* boot/src/tests/registrator/registerUser.ts: legacy fund::coopwallet
  (circulating_account/initial_account) → ledger2::accounts (счета 80, 86).
  После Epic 1 confirmreg перестал вызывать Ledger::add, поэтому
  legacy-баланс не пополняется. Теперь сравниваем приращение balance счёта
  80 (Паевой фонд, на который попадает minimum через PUT_MINSHARE) и
  счёта 86 (Целевое финансирование, через PAY_ENTRANCE).

* boot/src/tests/capital-import.test.ts: ожидаемый contributor.status
  скорректирован 'active' → 'import'. ImportContributor создаёт запись
  со статусом IMPORT (см. Status::IMPORT в contributors.hpp); перевод
  в ACTIVE — отдельным шагом.

* boot/src/tests/ledger2-read-layer.test.ts: фильтр accountId без
  actionNames возвращает все sibling-actions процесса (по дизайну
  репозитория). Тест явно передаёт actionNames=['debit','credit'],
  чтобы проверить только прямые проводки.

* boot/src/tests/capital.test.ts: regshare-идемпотентность — добавлен
  sleep(2000) перед повторным regshare, чтобы expiration транзакции
  отличался (иначе nodeos отклоняет как duplicate transaction).

* controller/schema.gql + sdk/zeus: регенерированы из ProcessRegistry
  и Ledger2-резолверов (operationCode/operationCodes вместо action*).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-25 07:07:45 +00:00
coopops 6df13c0e70 [989-9][@ant] test(boot): обновить ledger2-read-layer.test под operationCode
GraphQL HISTORY_QUERY: actionCode → operationCode; фильтр actionCodes →
operationCodes; ожидаемый код в filter-тесте mig.share → o.mig.share.

Регрессии после operations/processes refactor закрыты:
17 failed → 4 failed (84 → 86 passed). Оставшиеся 4 — pre-existing,
не связаны с рефакторингом нейминга:

  - capital-import: contributor.status='import' вместо 'active'
    (поведение capital-контракта, не наша область).
  - registrator x2: compareTokenAmounts на legacy
    fund::coopwallet.circulating_account.available, который не пополняется
    с Epic 1 (Ledger::add удалён).
  - ledger2-read-layer: фильтр accountId возвращает sibling-actions
    одного процесса (включая wallet_to=80000), тест ожидает строгий 51000.
    Pre-existing разрыв между документированным поведением фильтра
    (через process_hash IN ...) и ожиданиями теста.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-25 05:36:39 +00:00
coopops e8b323a1ec [989-9][@ant] refactor(ledger2): cooptypes — source of truth для operations/processes
* cooptypes/src/ledger2/operations.ts — LEDGER2_OPERATION_REGISTRY (18 записей),
  mirror `cpp/lib/core/ledger2/operations.hpp` (OPERATION_REGISTRY).
* cooptypes/src/ledger2/processes.ts — LEDGER2_PROCESS_REGISTRY (11 записей),
  mirror `processes.hpp`.
* Controller process-hash-locator: строит OPERATION_CODE_TO_PROCESS_TYPE
  из cooptypes; только backend-специфичный оверрайд (`o.cap.commit` →
  `p.cap.commit`) + PROCESS_HASH_LOCATOR (таблица/поле entity-hash).
  Никаких локальных хардкод-списков операций или процессов.
* Controller ProcessRegistryService: applyData.action_code → operation_code,
  OPERATION_CODE_TO_PROCESS_TYPE, SQL-колонка alias operationCode.
* Controller DTO/domain: actionCode → operationCode, actionCodes → operationCodes.
* TypeORM repository: `a.data ->> 'operation_code'`, alias "operationCode".
* SDK ledger2OperationSelector: actionCode → operationCode (zeus регенерится из
  обновлённой schema.gql при старте контроллера + generate-client).
* Desktop OperationsPage: actionCode → operationCode; локальный ACTION_LABELS map
  удалён — human-name тянется через Ledger2.getOperationHumanName из cooptypes;
  цветовая схема по второму сегменту `o.<contract>.<verb>`.
* Boot-тест process-registry: обновлён под новые имена (p.reg.accept, p.wal.depo,
  o.reg.payent, o.reg.putmin, o.wal.depcpl) и operation_code поле.

Типы ok (tsc controller, vue-tsc desktop), cooptypes собирается.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 19:28:27 +00:00
coopops 841e15e7a6 chore(ledger2): удалить локальные audit JSON из git, добавить в .gitignore
Файлы scripts/out/*.json — локальные выгрузки off-chain аудита,
случайно попавшие в предыдущий коммит. Возвращаю tree к чистому состоянию,
директория добавлена в .gitignore.
2026-04-24 18:39:06 +00:00
coopops 95a2e054fc [989-9][@ant] refactor(ledger2): operations/processes — переименование + префиксы o./p.
* actions.hpp → operations.hpp: namespace ledger2_ops → operations::<contract>::;
  ActionRegistryEntry → OperationRegistryEntry; ACTION_REGISTRY → OPERATION_REGISTRY;
  ledger2_find_action → find_operation.
* process_types.hpp → processes.hpp: namespace process_types → processes::<contract>::.
* eosio::name с префиксами: operation_code — `o.<contract>.<verb>` (PAY_ENTRANCE,
  LEND, REPAY, COMPLETE_DEPOSIT …), process_type — `p.<contract>.<noun>`
  (p.reg.accept, p.cap.debt, p.cap.rid, p.cap.prop, p.mkt.reqst, p.wal.depo …).
  wall → wal в eosio::name (в C++ namespace остаётся wallet).
* Параметр apply() переименован action_code → operation_code.
* Все 14 call-site в registrator/wallet/capital/marketplace/soviet обновлены.
* Пилотные YAML: reg.regist.standard.yaml → p.reg.accept.standard.yaml,
  wall.deposit.standard.yaml → p.wal.depo.standard.yaml, с обновлением
  process_type, operations[].ledger_code, transitions[].ledger_code, related[].
* Кроме основной цели — актуализированы ярлыки навигации в reports/install.ts
  (Операции → Реестр операций, Кошельки → Реестр кошельков, Счета → Реестр счетов).

Собраны ledger2, registrator, wallet, capital, marketplace, soviet — все wasm OK.

Источник правды: rename-operations-plan.md в bmad-output.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 18:38:44 +00:00
coopops f377f7ff25 [989-9][@ant] fix(reports): ФИО пайщика + переезд на q-table в табе «Пайщики»
* Грузим IAccount через accountStore.getAccounts (по паттерну ListOfParticipantsPage),
  чтобы получить private_account с ФИО. Таблица participants из контракта давала
  только username — ФИО оттуда не извлечь.
* В колонке «Пайщик» сверху — ФИО (getName), под ним мелким моноспейсом — username.
* Переписал кастомный <table> на q-table с динамическими колонками (по одной на
  активную программу) — теперь визуально согласован с AccountsPage/CoopWalletsPage.
  Сортировка работает по суммарной (available + blocked) ячейке.
* API-слой сузил до loadProgramsAndWallets(): programs + progwallets, без участников
  (их даёт accountStore).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 16:58:18 +00:00
coopops 371238cefb [989-9][@ant] fix(reports): табы кошельков в шапку + читаемые ячейки «пайщик × программа»
* WalletsPage — shell по паттерну DocumentsPage: useHeaderActions + RouteMenuButton,
  два child-route reports-wallets-coop / reports-wallets-participants (redirect на coop).
* Переименовал *Tab.vue → *Page.vue (теперь это полноценные страницы, не табы).
* В ячейках матрицы убрал JetBrains Mono и text-weight 500 — нормальный шрифт, bold только в Итого/Σ,
  размер 14px, иконки приглушены opacity 0.75. Читается как суммы на странице счетов.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 16:42:56 +00:00
coopops c65cac5eef [989-9][@ant] feat(reports): вкладка «Пайщики» на странице Кошельки
WalletsPage стала shell с q-tabs:
  • «Кооператив» — прежний список ledger2-кошельков (вынесен как есть в
    CoopWalletsTab.vue).
  • «Пайщики» — новый срез soviet.progwallets: матрица «пайщик × программа»,
    загружается напрямую через fetchTable (не через GraphQL, т.к. на
    странице нужны текущие blockchain-данные, а не postgres-индекс).

ParticipantWalletsTab:
  • Таблица: строки = accepted-пайщики (отсортированы по username);
    колонки = активные программы коопа (Цифр.Кошелёк, Благорост,
    Генератор, membership-программы и т.д.); ячейки — available сверху
    (зелёная монета) и blocked снизу (коричневый замок), нули бледнее.
    Итог на строке + строка Σ по программе внизу.
  • Членские взносы не показываем (per user feedback).
  • Ссылка «К операциям пайщика» справа → reports-operations?username=X.

OperationsPage: поддержка ?username=X — новый чип-фильтр «Пайщик %FIO%»
с clearUsernameFilter + передача в ILedger2HistoryFilterInput.username.
Сервер (GetLedger2HistoryInput) уже поддерживает поле username — добавлен
только клиентский path.

participant-wallets-api.ts — локальная api-функция loadParticipantWalletsMatrix,
читает scope=coopname из soviet.programs + .progwallets + .participants
и строит pivot-срез клиентски (под 6 коопов с ≤60 progwallets — в самый
раз, без пагинации).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 16:07:30 +00:00
coopops 3e4b2e959f [989-9][@ant] chore(reports): Скачать XML/PDF → «для отправки»/«для просмотра»
Терминология XML/PDF пустая для бухгалтера. По назначению:
  XML → в ФНС/СФР («для отправки»)
  PDF → распечатать/подписать/подшить («для просмотра»)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 12:44:25 +00:00
coopops 3cd0c9a810 [989-9][@ant] fix(reports): календарь → displayYear=due year; reportYear per-cell = displayYear - dueYearOffset
Баг: в 2026 году клик на БУХОТЧ открывал форму «Отчёт за 2026», хотя
председатель в апреле 2026 должен сдавать отчётность ЗА 2025. То же для
Q4 кварталок (NDFL6/RSV/FSS4) и декабря ПСВ — при dueYearOffset=1 в
январе/феврале/марте 2026 календарь относил ячейку к 2026, а не 2025.

Было: `year` календаря = reportYear (год ЗА который). dueYearOffset
учитывался только в calcDueDate, но в UI ячейка оседала в том же году.
Клик → форма получала year=calendarYear → всегда «за текущий».

Стало: `year` календаря = displayYear = календарный год СДАЧИ.
Для каждой ячейки reportYear = displayYear - entry.dueYearOffset.
  - БУХОТЧ март 2026 → reportYear=2025 (годовая сдача)
  - Q4 (NDFL6/RSV/FSS4) февр/январь 2026 → reportYear=2025
  - ПСВ январь 2026 (декабрь prev) → reportYear=2025
  - Q1..Q3 кварталок + ПСВ фев..дек → reportYear=displayYear (без сдвига)

DTO ReportCalendarPeriodEntry: добавлено поле reportYear (Int!). Фронт
эмитит entry.reportYear — форма открывается за правильный период.

Backend: archive/drafts/marks читаются за displayYear-1 и displayYear,
ключ (reportType, period, year) чтобы не смешивать статусы 2025 vs 2026
в одной ячейке. calcDueDate как было — принимает reportYear, применяет
offset к году для реальной даты.

Schema.gql / zeus — регенерированы.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 11:08:14 +00:00
coopops a854468e8c [989-9][@ant] test(reports): XSD-валидация it.each по всем периодам всех генераторов
Аудит после бага ЕФС-1 Q4 → '0': проверил все XSD-схемы на enum-ограничения
и сверил с hard-code в генераторах. Других ошибок маппинга нет, но XSD-тест
гонялся только на один период в каждом генераторе — если завтра кто-то
поменяет `switch (quarter)` обратно на '0', баг снова всплывёт в проде.

Теперь XSD-валидация iterates по всем реально допустимым периодам:
- NDFL6    it.each Q1..Q4  (enum 21/31/33/34)
- RSV      it.each Q1..Q4  (enum 21/31/33/34)
- PSV      it.each M1..M12 (enum 01..12)
- UV_VZNOSY it.each M1..M12 (enum 21/31/33/34 + НомерМесКварт 11..13)
- UUSN     it.each Q1..Q4  (enum 21/31/33/34 + НомерМесКварт 01..04)
- FSS4     уже покрыт Q1..Q4 (предыдущий коммит)

BUHOTCH/DUSN — yearly, hardcode Период='91'/'34', enum XSD {34,91..94}/{34,50,95,96} —
оба в enum, покрыты существующим single-path тестом.

Тестов: 71 → 102 (+31 XSD-прогона).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 10:45:44 +00:00
coopops c1ef03876a [989-9][@ant] fix(reports): ЕФС-1 Q4 → Код '12' (а не '0') для XSD {03,06,09,12}
Баг: при скачивании ЕФС-1 за Q4 попадала ошибка XSD
  «The value '0' is not an element of the set {'03','06','09','12'}».
XSD efs1.xsd требует код = месяц окончания квартала: 03|06|09|12.
Автор считал «год (IV) = 0», но ЕФС-1 не бывает годовым — Q4 → декабрь → «12».

Тесты:
- Старый «квартальные коды СФР: 03/06/09/0» фиксировал баг — переписан на
  «03/06/09/12».
- XSD-валидация была только на Q1. Теперь — it.each по всем 4 кварталам.

У RSV другая система (ФНС-коды 21/31/33/34), не пересекается. PSV — месячная,
собственная мапа 1..12. Затронут только Fss4Generator.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 10:39:54 +00:00
coopops a1d67d7d35 [989-9][@ant] fix(reports): q-form + кнопка сохранить + нативный mask-блок ввода
SettingsPage:
- Убрали автосохранение — сервер дёргаем только по клику «Сохранить реквизиты».
- Обернули всё в <q-form greedy>: валидация всех полей перед @submit. Если
  хоть одно красное — @validation-error, save() не вызывается, ошибки летят
  только локально, никакого server-5xx из-за неполного ввода.
- Кнопка сохранить живёт в sticky save-bar внизу страницы (не прыгает в шапку).
  Рядом компактный статус: «Реквизиты сохранены» / «Ошибка сохранения».
- Placeholder'ы — правила ввода, не примеры: «1–3 цифры» вместо «16»,
  «5 цифр» вместо «20200», «XX.XX или XX.XX.XX» для ОКВЭД.

RequisiteField:
- Для фикс-длинных цифровых полей используем Quasar-mask (`#` = только цифра,
  буквы блокируются на keypress нативно, в поле вообще не появляются).
- Для ОКВЭД (digits + точки, переменная длина) — @keydown-блокер + @paste-
  блокер: буквы не попадают в поле даже на мс.
- Убрали digitsOnly-проп — его задачу теперь решает mask.
- Добавили pattern + patternMessage для СНИЛС/СФР (частичный ввод с мaskой
  не даёт сохраниться).

Масks/правила по полям:
  ОКВЭД    digits+dots, maxLen 8,  паттерн XX.XX(.XX)?
  ОКФС     mask ###        (1–3 цифр)
  ОКОПФ    mask #####      (ровно 5)
  ОКТМО    mask ###########, exactLengths [8, 11]
  ОКПО     mask ##########,  exactLengths [8, 10]
  СНИЛС    mask ###-###-### ##, pattern \d3-\d3-\d3 \d2
  СФР      mask ###-###-######, pattern \d3-\d3-\d6

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 08:29:01 +00:00
coopops d621f30f59 [989-9][@ant] fix(reports): маски+правила длины на классификаторах, автосейв по blur, компактный stub
RequisiteField:
- Новые props: digits-only, digits-dots-only, max-length, exact-lengths (ИЛИ),
  pattern + pattern-message. Фильтр на input режет недопустимые символы до
  эмита, maxlength режет длину. lazy-rules — валидация только после первой
  потери фокуса (не атакуем пользователя красным пока он печатает).
- Форвардит @blur наверх — для savetrigger родителя.
- Нативный required по rules, без отдельного :error-prop.

SettingsPage:
- Автосохранение теперь по blur поля (600ms coalescing debounce на случай
  быстрого tab-переключения), не по input. Раньше сохраняло пока пользователь
  ещё печатал → ловил «ОКТМО должен быть 8 или 11 цифр» на частично
  набранном «123».
- Классификаторы: ОКВЭД (digits+dots, pattern 94.99/46.73.7), ОКФС (1–3 digits),
  ОКОПФ (mask #####), ОКТМО (8|11 digits), ОКПО (8|10 digits). СНИЛС/СФР —
  маски оставлены. Должность председателя — maxLength=100, репдок — maxLength=200.

ReportEditorDialog (stub readiness):
- q-list с длинным reason для каждого поля заменён на компактный ряд
  q-chip-ов с label. Reason-ы съедали воздух и повторяли одно и то же
  для 5 классификаторов — теперь один заголовок + 5 чипов.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 08:13:41 +00:00
coopops 6ca9997573 [989-9][@ant] fix(reports): gate по реквизитам + автосейв в SettingsPage + убрали лишние бейджи
DocumentsPage/ReportEditorDialog:
- Перед рендером формы вызываем checkReportReadiness(reportType). Если ready=false —
  показываем stub «Сначала заполните реквизиты» со списком недостающих полей и
  кнопкой «Перейти к реквизитам» (navigate → reports-settings?focus=<key>).
- Форма/черновик/кнопки Скачать XML/PDF не грузятся до заполнения реквизитов
  (раньше XML скачивался даже при пустом СНИЛС подписанта). Отметки «не надо
  сдавать» / «сдан вне платформы» доступны независимо от gate.
- Поправили tooltip «Перегенерировать» — убрали упоминание блокчейна (данные
  хранятся в БД).

SettingsPage:
- Убрали кнопку «Сохранить реквизиты» сверху — автосохранение через debounce
  (600ms) по любому изменению поля/signerType. Статус «Сохраняется…/Сохранено/
  Ошибка» — маленький чип в заголовке карточки. onBeforeUnmount дописывает
  последнюю правку синхронно, если таймер ещё не сработал.
- Убрали подписи «Данные из блокчейна (read-only)» и «Ручной ввод» — данные
  в БД, user-speak. Заголовки карточек сохранили.

RequisiteField:
- Убрали цветные бейджи Блокчейн / Ручной ввод / Не заполнено. Вместо
  «Не заполнено»-бейджа — нативная q-input-валидация: пустое required-поле
  подсвечивается красным outline + error-message «Обязательное поле».
  Звёздочка * в label отмечает обязательные поля.
- Read-only поля из БД — через :readonly+:disable, без отдельного бейджа.

OperationsPage:
- Сумма в таблице — bold + text-grey-10 для контраста. В мобильном grid-item
  добавили блок «Сумма» с text-body1.text-weight-bold.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 08:04:32 +00:00
coopops eeeca0fe61 [989-9][@ant] fix(reports): сумма в таблице операций + «Пайщик» вместо «Исполнитель» + UX-мелочи
- OperationsPage: колонка «Сумма» (apply.quantity/amount) + «Пайщик» вместо «Исполнитель» + бейдж «Тип процесса: <wall.depcpl>» с копированием
- WalletsPage: кнопка «К операциям» в хедер раскрытой секции (вместо прижатой снизу) + ограничение ширины memo (240px, word-break)
- AccountsPage: аналогично — кнопка «Все операции» в хедер истории проводок

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-24 04:44:05 +00:00
coopops 46f3b71f83 [350-1][@ant] fix(standards/FocusBar): убрать осиротевший relatedCount — computed больше не используется после удаления хинта под «Конец процесса», vue-tsc валился TS6133 2026-04-24 03:21:03 +00:00
Alex Ant 32592fded2 chore(release): publish 2026-04-24 01:38:37 +05:00
Alex Ant db356628c9 chore(release): publish 2026-04-24 01:38:16 +05:00
coopops bbae1b5606 Merge branch 'standards/registrator' into dev
[350-1][@ant] merge(standards): регистратор — три сценария (reg.regist / reg.adduser / reg.recovery) + slim-рефактор wall.deposit + расширение схемы YAML (actions[].links, documents[].registry_id) + UI-рендер ссылок между стандартами и «Документы»-карточки в FocusBar
2026-04-23 20:29:21 +00:00
coopops c7e634344e [350-1][@ant] fix(standards/FocusBar): убрать хинты под «Конец процесса» — подсказки про финал и про связанные стандарты убраны, оставлена только строка с code+human+badge; текст допишем когда появится content который реально нужен на этом узле 2026-04-23 20:29:00 +00:00
coopops f98d39cc83 [350-1][@ant] fix(standards): END-нод не дублирует описание финал-статуса + reg.adduser → «Приглашение пайщика» — END-карточка теперь показывает только имя финала (code+human+badge) со ссылкой «см. карточку статуса», а полное описание остаётся единственным в самой active-вершине, чтобы не было одинакового текста на двух узлах; reg.adduser переименован в «Приглашение пайщика» с узким смыслом: вводит в цифровой кооператив ранее принятого пайщика с бумажным заявлением (убран пример «заочное голосование общего собрания» — он не применим), описание покрывает что пайщику отправляется ссылка на установку ЭЦП, которую он активирует сценарием reg.recovery, связанные стандарты reg.regist и reg.recovery согласованы с новым именем 2026-04-23 20:23:01 +00:00
coopops 52d2ce67ab [350-1][@ant] polish(standards/reg.regist): контракты с заглавной + слово «контракт» + Кассир + ссылки на Gateway + правильные registry_id — «в Gateway» везде стало «в контракте Gateway», ledger2-термины заменены на «операции переводов и проводок» и «контракт книги учёта Ledger2» где это читается естественнее, actor «Оператор Gateway» → «Кассир» на confirmpay/declinepay с ссылками на будущий стандарт gate.inpay (обработка входящего платежа), «повестка joincoop» уточнено как «повестка типа «joincoop»», протокол решения совета подписывает председатель совета (не все члены), registry_id документов уточнены из cooptypes/registry — заявление 100.ParticipantApplication, решение 501.DecisionOfParticipantApplication; переформулирован active-статус — без повторения с confirmreg, теперь описывает полезный результат: что на каком кошельке оприходовано и что пайщик теперь может делать дальше 2026-04-23 20:12:49 +00:00
coopops 40ae21854b [350-1][@ant] fix(standards): убрать фейковую joincoop-повестку из documents reg.regist — в reguser.cpp параметр document2 только один (statement), а joincoop это soviet::newpackage-вызов без document2-подписи; присвоил registry_id:100 самому заявлению на вступление 2026-04-23 19:52:07 +00:00
coopops ec2cc9d7fa [350-1][@ant] feat(standards): ссылки между стандартами из действий + документы как registry_id + правки reg.regist — добавлено поле actions[].links[]{process_type,label} для кнопок-переходов к родственным стандартам (совет по confirmreg → sov.decision), документы расширены полем registry_id (числовой код в реестре) и отвязаны от legacy scenario[step]→action (slim: doc.action прямо), в reg.regist исправлен actor с «Пайщик» на «Кандидат» на reguser, добавлена joincoop-повестка как документ с registry_id:100 (сейчас это единственный известный код, остальные с registry_id:0+TODO), FocusBar на действии показывает колонку «Документы» (иконка+название+код) и блок «Перейти» с кнопками к связанным стандартам, чтобы председатель мог одним кликом провалиться в процесс принятия решения советом когда смотрит стандарт регистрации 2026-04-23 19:40:08 +00:00
coopops b2caa26948 [350-1][@ant] feat(standards): реестр стандартов регистратора + slim-рефактор пилотов — описаны три сценария вокруг сущностей candidate/account (reg.regist, reg.adduser, reg.recovery), формат приведён к v1-спеке требования a2 (§сценарий убран, id:public_* и roles[] убраны, documents[].action, transition-поля упрощены), чтобы председатели видели исчерпывающий набор on-chain-сценариев регистратора в едином источнике правды; reg.adduser и reg.regist используют одни и те же ledger2-коды (reg.minshare/reg.entrfee — одна операция триггерится из разных действий), reg.recovery документов/проводок не имеет — оффчейн-инвайт + один on-chain changekey; пилот wall.deposit переведён в тот же slim-формат для согласованности 2026-04-23 19:01:37 +00:00
Alex Ant d104a9e037 chore(release): publish 2026-04-23 22:27:50 +05:00
Alex Ant 0bcca3892e chore(release): publish 2026-04-23 21:04:11 +05:00
Alex Ant e3a45b0444 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-04-23 21:03:38 +05:00
coopops 9491789d6c [549-26][@ant] ci: вернуть временно сборку и push dicoop/cooparser — деплой testnet/production ещё привязан к этому образу, миграция потребителей на dicoop/parser из отдельного coopenomics/parser repo не завершена; убираем шаг повторно после того как webhook-endpoints переключатся на новый образ, сейчас падение деплоя критичнее чем дубликат publish-пути 2026-04-23 14:36:39 +00:00
coopops c10dcf856d [350-1][@ant] ci: переставить копирование standards-site из site/ в docs/ ДО mkdocs build — тот же паттерн что graphql/sdk/cooptypes; mkdocs wipe-ит site/ и надёжно тащит статику в итог через docs/, иначе dist не попадал в gh-pages 2026-04-23 14:09:25 +00:00
Alex Ant 5e58f08201 chore(release): publish 2026-04-23 18:53:33 +05:00
Alex Ant 8d890c89a4 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-04-23 18:53:07 +05:00
Alex Ant 6586692d84 Merge pull request #361 from coopenomics/fix/payment-card-ssr-ts
fix(desktop): vue-tsc зелёный в PaymentCard — каст payment.id к string
2026-04-23 18:51:56 +05:00
coopops 53c93d805a [989-4][@ant] fix(desktop): vue-tsc зелёный в PaymentCard — каст payment.id к string
Zeus-скаляр ID разворачивается как непрозрачный `{}`, поэтому `:id='payment.id'`
не присваивался string-пропу кнопок. Явный `String(payment.id)` убирает обе ошибки
vue-tsc без изменения runtime-поведения (v-if уже гарантирует truthy).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:49:58 +00:00
coopops c3e8f6392d [989-9][@ant] refactor(desktop): ledger2-реестры → re-export из cooptypes
После мёржа graph-standarts → dev реестры ledger2 живут в
components/cooptypes/src/ledger2/{accounts,wallets}.ts. Desktop-копии
становятся тонкими re-export-обёртками, публичный API путь
src/shared/lib/ledger2 сохранён (AccountIdCell / WalletIdCell не трогаем).

- account-registry.ts: локальный массив и 4 хелпера заменены на re-export
  Ledger2.{LEDGER2_ACCOUNT_REGISTRY,getAccountName,getAccountMeta,storedIdToCode}.
- wallet-registry.ts: аналогично для LEDGER2_WALLET_REGISTRY и getWalletName.
- Типы AccountKind/AccountMeta/WalletMeta — re-export из Ledger2-namespace.
- Контент реестров в cooptypes один-в-один совпадает с тем, что было в
  desktop (проверено diff'ом). При добавлении счёта/кошелька теперь
  править только cooptypes + contract, второй поток (desktop) подхватит
  автоматически.

Попутно zeus-файлы (controller/zeus + sdk/src/zeus) регенерированы после
rebase на origin/dev — никаких semantic-изменений, только нормализация
порядка экспортов.

Закрывает blago issue 989-9 (подтянуть cooptypes с ledger2-реестрами).
2026-04-23 13:39:55 +00:00
Alex Ant 7753fffbac chore(release): publish 2026-04-23 18:33:04 +05:00
Alex Ant 6929c72d2c Merge branch 'dev' of github.com:coopenomics/mono into dev
Made-with: Cursor

# Conflicts:
#	components/parser/package.json
2026-04-23 18:32:17 +05:00
coopops ad9ae58026 [989-9][@ant] docs(reports): финализация BMad + эпик после возврата unit-тестов
- sprint-status STORY-4-6 acceptance_criteria: плюс строка про 68 живых
  тестов генераторов (ранее были debt, сейчас закрыто).

Эпик 989-9 CLOSED полностью: 22 чекпоинта выполнены, STORY-3-4 (E2E)
обоснованно отклонён, 0 открытых debt-пунктов.
2026-04-23 13:30:46 +00:00
coopops 46872cd304 [989-9][@ant] test(reports): переписать фикстуры на edits-shapes, вернуть 68 живых тестов
После рефактора генераторов в Sprint 1/2 (на BuhotchEditsShape /
ZeroReportEditsShape) старые фикстуры передавали legacy ReportInput →
все 45 тестов падали на undefined 'header.idFile'. Ранее пометил
describe.skip'ом, сейчас переписал честно.

- Две фикстуры ПК «Ромашка» вместо legacy baseInput:
  - buhotchBaseEdits: BuhotchEditsShape (с explicit header/organization/
    signer/balance/notes). Балансы по умолчанию нули; тест «выплёвывает
    суммы в СумОтч/СумПрдщ/СумПрдшв» сам подставляет конкретные числа.
  - zeroBaseEdits: ZeroReportEditsShape для всех 7 нулёвок, + helpers
    withPeriod(period) / withYear(year) для per-test оверрайдов.
- Тест «считает балансы из ledger в тыс.₽» заменён на «выплёвывает
  edits.balance.* дословно». Ledger→balance-конвертация — ответственность
  ReportEditsBuilderService, не генератора (разделение слоёв).
- Тест имени файла теперь «эхом возвращает header.idFile в fileName и
  атрибут ИдФайл». Формат имени строит builder; генератор — просто эхо.
- Тест «без sfrRegNumber» для ЕФС-1: передаём signer.sfrRegNumber=null
  вместо удаления поля.
- ReportRegistryService.getAll() → getAvailableReports() (актуальное API).
- import ReportInput удалён.

Результат: 68 passed / 0 failed / 0 skipped. XSD-валидация для всех 5
MVP-форм + 2 legacy снова в CI-гейте. Сверка с ПК «Ромашка» эталонами
(6 тестов) — работает.
2026-04-23 13:30:46 +00:00
coopops 17f8cf7007 [989-9][@ant] chore(reports): закрыть эпик — отклонить E2E, зафиксировать test-debt
- BMad sprint-status.yaml: STORY-3-4 (E2E) → rejected с reason (UI активно
  переделывается, инфра Playwright отсутствует, возврат — отдельный спринт
  «QA/автоматизация» после стабилизации MVP). Sprint 4 → completed.
- STORY-4-6 (debt-organize) acceptance_criteria актуализированы:
  PDF 4 нулёвок выполнено post-sprint; Blago-server sync подтверждён;
  Prod-календарь расширен до 2029.
- controller/tests/unit/reports/report-generators.test.ts: блоки, работающие
  через legacy ReportInput, помечены describe.skip с общим TODO. После
  рефактора генераторов на edits-shapes (Sprint 1-2) фикстуры не были
  переписаны — отдельный заход. Работоспособность покрыта UI + XSD-проверкой.
2026-04-23 13:30:46 +00:00
coopops 64b224c903 [989-9][@ant] feat(reports): PDF для 5 MVP-форм + календарь РФ 2028-2029
Оставшиеся задачи из Sprint 4 debt (кроме E2E — это отдельная инфра-работа).

- ReportEditorDialog: кнопка «Скачать PDF» теперь работает для всех 5 MVP-форм
  (BUHOTCH/NDFL6/RSV/PSV/FSS4). Paper-view компоненты уже имели идентичный
  контракт `{xml, requisites?, year?}` и `.printable-form`-root — просто
  подключил Ndfl6Form/RsvForm/PsvForm/Efs1Form к `.hidden-pdf-source` по
  `v-else-if` на reportType. Добавлен computed `hasPdfPaperView` +
  PDF_SUPPORTED_TYPES как единый источник правды.
- reports-calendar-registry: RU_HOLIDAYS_BY_YEAR расширен на 2028–2029
  (срок БУХОТЧ за 2026 сдаётся 31.03.2027; при планировании за 2027 —
  31.03.2028). Захардкоженные даты вынесены в общий BASE_RU_HOLIDAYS.
- widgets/report-forms/README обновлён: снято упоминание Sprint 3 debt.

Blago-server sync — подтверждено актуальным (pull завершён, нет расхождений).
Остаётся в debt только STORY-3-4 E2E happy-path — нет Playwright-инфры
под reports-экстеншн, отдельный заход с запущенным стендом.
2026-04-23 13:30:46 +00:00
coopops 81488d381d [989-9][@ant] feat(reports): мобильная адаптивность редактора и календаря
- ReportEditorDialog.action-panel на <md экранах становится slide-in overlay
  справа (width: min(85vw, 320px)), открывается кнопкой-слайдером в q-bar,
  закрывается backdrop-тапом или кнопкой «Скрыть» в панели. На ≥md — как
  было, inline-колонкой справа. Переход между режимами на ресайзе автоматом.
  Raison d'être: панель 260px на mobile перекрывала форму, редактировать
  было невозможно.
- ReportsCalendar: 5×12 матрица в .calendar-scroll-обёртке с overflow-x:auto,
  grid имеет min-width:900px и min-col 54px — ячейки не прессуются, пользователь
  свайпает горизонтально. Раньше грид ломал вёрстку на узких экранах.
2026-04-23 13:30:46 +00:00
coopops e52eae02d1 [989-9][@ant] fix(reports): defineModel в editor'ах + XSD-точные лейблы чекбоксов
Bug: q-checkbox «Достоверность подтверждена аудитором»/«Утверждено общим
собранием» и q-option-group «Подписант/Уполномоченный представитель»
визуально не переключались (управляемые Quasar-контролы ждут реальной
смены :model-value). q-input-поля казались рабочими, т.к. нативный input
сам показывает набранный символ до синка с моделью.

Причина — паттерн :edits + @update:edits + structuredClone(reactive-proxy)
в BuhotchEditor/ZeroReportEditor давал сбой: у Vue-proxy есть служебные
traps (__v_raw и т.п.), structuredClone на нём отрабатывал неочевидно,
эмит не пробрасывал новый объект как нужно.

- BuhotchEditor & ZeroReportEditor: defineModel<TEdits>('edits') (Vue 3.4+)
  вместо prop+emit. Внутри — JSON.parse(JSON.stringify(current)) вместо
  structuredClone — чисто POJO, без риска proxy-трапов.
- ReportEditorDialog: v-model:edits на оба редактора + writable computed
  с get/set, пишущим в общий useReportDraft.edits (один source of truth).
  Убраны лишние onBuhotchEditsUpdate/onZeroEditsUpdate handler'ы.
- BUHOTCH-лейблы приведены к XSD (NO_BOUPR_1_159_00_05_04_01):
  - «Достоверность подтверждена аудитором» → «Подлежит обязательному
    аудиту» (атрибут ПрАудит, обычно 0 для кооперативов).
  - «Утверждено общим собранием» → «Подлежит утверждению общим
    собранием» (атрибут ПрУтвер, =1 для потребкооперативов по ст.38 ФЗ-193).
  - Оба с тултипом-подсказкой для бухгалтера.
2026-04-23 13:30:46 +00:00
coopops 88cd454c5b [989-9][@ant] fix(reports): reload календаря после диалога + ПСВ все 12 месяцев
- ReportsCalendar: defineExpose({ reload }). DocumentsCalendarPage держит
  template-ref на виджет и дёргает reload() в onMarked/onGenerated.
  Раньше reportStore.loadCalendar() возвращал свежие данные, но не пушил
  их в widget.rows — статус ячейки обновлялся только при ре-маунте страницы.
- psvEntries: 12 месяцев вместо 8. ПСВ — ежемесячная по ст.431 НК РФ;
  послабление ФНС про м3/м6/м9/м12 (закрываются РСВ) не отсутствие формы,
  а опциональное правило — пользователь сам отмечает «Не надо сдавать»
  на нужных ячейках. Декабрь: dueYearOffset=1 (срок 25.01 следующего года).
2026-04-23 13:30:46 +00:00
coopops 55f76368f4 [989-9][@ant] feat(reports): «Отметить сданным» + производственный календарь РФ (Sprint 4 доп)
Добавка к Sprint 4 по фидбеку: нужна кнопка ручной отметки «отчёт сдан сторонне»
(бумагой / через Контур / СБИС) — чтобы ячейка календаря была зелёной без
реального XML в нашем архиве.

- Enum ReportSubmissionMark: добавлен SUBMITTED_EXTERNALLY к NOT_REQUIRED.
- CalendarEntryStatus: добавлен SUBMITTED_EXTERNALLY.
- Приоритет статусов: SUBMITTED > SUBMITTED_EXTERNALLY > DRAFT > NOT_REQUIRED > OVERDUE > EMPTY.
- CalendarCell: SUBMITTED_EXTERNALLY — зелёная точка с обводкой-кольцом
  (визуально отличается от реальной сдачи).
- ReportEditorDialog: 3-state mark (null / NOT_REQUIRED / SUBMITTED_EXTERNALLY);
  если реальный XML сдан — кнопок нет, только баннер; иначе 2 кнопки или «Снять отметку».
- reports-calendar-registry: production-календарь РФ 2026-2027 (8 января,
  23 февраля, 8 марта, 1 и 9 мая, 12 июня, 4 ноября). shiftToBusinessDay
  делает двойной перенос (Sat/Sun/праздник → ближайший рабочий), max 14 итераций.
- BMad sprint 4 completed 10/10 pts; STORY-3-4 E2E + PDF 4 нулёвок + prod-деплой
  blago-server — остаются как debt (блокеры инфры).
2026-04-23 13:30:45 +00:00
coopops 48e4f3a7d6 [989-9][@ant] feat(reports): хедер-навигация + NOT_REQUIRED-отметка + перенос выходных (Sprint 4)
- DocumentsPage → shell с router-view + 3 кнопки шапки через useHeaderActions
  (паттерн capital/ProjectPage). Child-маршруты reports-documents-{calendar,forms,archive},
  дефолт — календарь. Старые q-tabs удалены.
- ReportSubmissionMarkEntity (coop-wide) + мутация markReportPeriod — отметка
  «не надо сдавать» на ячейку календаря. Приоритет в резолвере:
  SUBMITTED > DRAFT > NOT_REQUIRED > OVERDUE > EMPTY.
- CalendarCell: submitted=зелёная точка (без заливки), overdue=насыщенный красный fill,
  not_required=серый ⊘. Сравнения через Zeus.CalendarEntryStatus.*.
- reports-calendar-registry: shiftToBusinessDay (Sat/Sun → Mon). Праздники РФ — debt.
- В ReportEditorDialog — toggle-кнопка «Не надо сдавать» / «Снять отметку»
  с confirm; после ok — reload календаря и закрытие диалога.
- BMad sprint-status: Sprint 1/2/3 → completed; Sprint 4 (STORY-4-1..6);
  STORY-3-4 E2E перенесён в debt.
2026-04-23 13:30:45 +00:00
coopops dad79c8449 [989-9][@ant] feat(reports): календарь отчётности 5×12 + табы в DocumentsPage (stories 3-1..3-5)
Backend (3-1):
- reports-calendar-registry.ts — хардкод сроков 5 MVP-форм:
  БУХОТЧ 31.03 след.года, 6-НДФЛ/РСВ/ЕФС-1 квартальные до 25-го,
  ПСВ ежемесячно кроме последнего месяца квартала.
- ReportCalendarRowDTO + CalendarEntryStatus enum (submitted/draft/
  overdue/empty).
- ReportCalendarResolver.getReportCalendar(year) — параллельно тянет
  архив и драфты на год, матрицит статусы.

SDK:
- reportCalendarSelector + queries/reports/getReportCalendar.ts.

Frontend (3-2 / 3-3):
- widgets/reports-calendar/ReportsCalendar.vue — матрица 5×12 с
  навигацией ± год, tooltip'ами и кликом по ячейке →
  @select(reportType, year, period) → открытие ReportEditorDialog.
- CalendarCell.vue — одна ячейка (status-цвета, иконки, тултип).
- DocumentsPage: q-tabs (Календарь / Список форм / Архив), календарь по
  дефолту. ReportEditorDialog открывается из обеих вкладок + из календаря.

Docs / lint (3-5):
- widgets/report-forms/README.md обновлён (editable + paper-view split).
- widgets/reports-calendar/README.md — архитектура календаря + известные
  ограничения (переносы на выходные — в долг).
- Почищены unused imports в report.dto.ts, non-null в fss4.generator.ts.
  Lint по reports extension и desktop/reports/ — чист.

STORY-3-4 (E2E happy-path) оставляем как долг — нужен отдельный сетап
playwright-сценария с реальным контроллером и фикстурой юзера-chairman.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:45 +00:00
coopops d354cd8ae8 [989-9][@ant] fix(reports): восстановить schema.gql (generate-schema падал на правах на логи)
В предыдущем коммите 172f0f2 schema.gql обнулилась из-за того, что
generate-schema завершался EACCES на попытке записи в
logs/application-2026-04-23.log (файл создан ранее root-процессом из
контейнера). Nest-logger ронял процесс до финальной записи schema.

Сейчас лог удалён, generate-schema отработал до конца —
schema.gql = 12511 строк, 225 типов, включая ZeroReportEdits*,
FieldError, BuildInitialReportEdits и validateReportEdits/
generateReportFromEdits мутации.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:44 +00:00
coopops 9e63881842 [989-9][@ant] feat(reports): 6 форм на edits-архитектуру + ZeroReportEditor (stories 2-5/2-6/2-7)
Backend (2-5/2-6):
- ZeroReportEditsShape — общий POJO для 6 нулёвок: NDFL6/RSV/PSV/DUSN/UUSN+
  UV_VZNOSY/FSS4. Per-type отличия в генераторе (КНД/ВерсФорм/periodCode/КБК),
  структура edits одна.
- ZeroReportEditsInputDTO/DTO + регистрация ZeroSignerType GraphQL-enum.
- ReportEditsBuilderService.buildZeroReport: дефолты из requisitesService
  (inn/kpp/orgName/oktmo/okved/ogrn/snils/sfrRegNumber/chairmanPosition).
- Рефакторинг 6 генераторов: generate(input: unknown) as ZeroReportEditsShape.
  Общие хелперы xml-utils: addFlexibleSignerFromShape, addHeaderMeta.
  Legacy-генераторы zero-report.generator.ts и createZeroReportGenerator
  удалены — больше не используются.
- validateReportEdits: non-BUHOTCH → ZeroReportEditsInputDTO + class-validator.
- HIDDEN_IN_MVP теперь прячет DUSN/UUSN/UV_VZNOSY (УСН-специфичные) вместо
  PSV — реальный MVP-набор это BUHOTCH/NDFL6/RSV/PSV/FSS4.

Frontend (2-7):
- ZeroReportEditor.vue — универсальный для 5 нулёвок. Per-reportType:
  * periodKind: quarter (NDFL6/RSV/UUSN/FSS4) / month (PSV/UV_VZNOSY) / none
  * needs.oktmo (NDFL6/DUSN/UUSN/UV_VZNOSY)
  * needs.snils (PSV — обязателен)
  * needs.sfrExtras — ОКВЭД/ОГРН/sfrRegNumber/chairmanPosition (FSS4)
- ReportEditorDialog: v-if разветвляется на BuhotchEditor ↔ ZeroReportEditor
  по reportType; заглушка убрана. PDF-кнопка отключена для non-BUHOTCH
  (paper-view *.Form.vue остаются read-only XML-парсером — PDF для них
  добавим в Sprint 3 когда будет календарь).
- DocumentsPage MVP_REPORT_TYPES: DUSN → PSV.

Все формы проходят через единый flow: buildInitialReportEdits (дефолты
⊕ dirty-merge) → редактор → validateReportEdits (inline подсветка) →
generateReportFromEdits (XSD-проверка → архив).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:44 +00:00
coopops 39c3ae9d3b [989-9][@ant] feat(reports): XSD-паттерны в SDK + validateReportEdits + подсветка полей (stories 2-1/2-2/2-3)
SDK (STORY-2-2):
- selectors/reports/patterns.ts — regex-константы и reportRules helper
  (inn/innUl/kpp/ogrn/okved/oktmo/okfs/okopf/okpo/snils/sfrRegNumber/
  dateDdMmYyyy/kbk + length/optionalRegex). Единый источник для форм.
- selectors/reports/fieldErrorSelector.ts — селектор { path, message }.
- queries/reports/validateReportEdits.ts — SDK wrapper.

Backend (STORY-2-1):
- FieldErrorDTO + резолвер validateReportEdits(reportType, editsJson).
- Валидация через class-validator + plainToInstance → BuhotchEditsInputDTO.
- flattenValidationErrors: ValidationError[] → FieldError[] с точечным
  JSONPath (organization.inn, balance.assetsTotal.otch). Совпадает с
  editedFields, которые трекает клиент — прямой matching для подсветки.

Frontend (STORY-2-3):
- useReportDraft: fieldErrors Record<path, string[]>, isValid, validateNow
  с debounce 500мс после каждого markDirty. При правке поля — локально
  сбрасываем его ошибки (не ждём сервер).
- BuhotchEditor: новый prop fieldErrors, helpers errFor/msgFor; каждое
  q-input получает :error / :error-message по JSONPath.
- ReportEditorDialog: валидационный бейдж в action-панели (ok/bad),
  счётчик ошибок; скачивание XML/PDF блокируется если не isValid.
- Все rules в BuhotchEditor переехали на reportRules.* — regex больше
  не хардкодится, единый источник истины = SDK patterns.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:44 +00:00
coopops 172216e60c [989-9][@ant] fix(reports): ReportEditorDialog — immediate:true на watcher, иначе форма пустая
DocumentsPage монтирует диалог через v-if='showEditor' — на момент setup()
props.modelValue уже true, классический watcher false→true не срабатывает
ни разу. load() не вызывается, edits остаются null, BuhotchEditor не
рендерится (v-if='edits'). Виден пустой экран без ошибок.

Решение — immediate: true: watcher отрабатывает на mount, проверяет что
modelValue=true и reportType=BUHOTCH, запускает load + loadRequisites.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:44 +00:00
coopops ece3c5b938 [989-9][@ant] feat(reports): ReportEditorDialog — интеграция editable-редактора БУХОТЧ в UI
Фикс к 791f269d: в прошлом коммите BuhotchEditor был написан, но не подключён —
пользователь по-прежнему видел старый read-only flow. Теперь:

- DocumentsPage: openEditor(r) → открывается ReportEditorDialog.
  Промежуточный ввод реквизитов/corrections больше не нужен (данные уже
  в requisites + ledger2, редактируются внутри формы).
- ReportEditorDialog — фулскрин, слева BuhotchEditor (editable, q-input
  с rules по XSD), справа панель: Скачать XML, Скачать PDF, Перегенерировать
  (dirty-merge), Удалить черновик, статус autosave.
- useReportDraft загружает edits через buildInitialReportEdits, autosave
  500мс, dirty-tracking JSONPath. PDF-экспорт — через скрытый paper-view
  BuhotchForm.vue + html2pdf.
- Для не-BUHOTCH форм показываем заглушку «Sprint 2».
- Удалены GenerateReportDialog.vue + ReportPreviewDialog.vue — оба пути
  поглощены ReportEditorDialog.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:43 +00:00
coopops b673004469 [989-9][@ant] feat(reports): backend+frontend основа редактируемых форм (stories 1-1..1-7)
Эпик 989-9 «Редактируемые inline-формы отчётов + календарь» — конец Sprint 1
(end-to-end путь на BuhotchForm: draft → dirty-merge → редактор).

Backend:
- ReportDraftEntity + CRUD-резолверы save/get/list/delete (uq по owner+type+year+period).
- BuhotchEditsDTO — зеркало XML БУХОТЧ с regex-паттернами из XSD; общий
  domain/patterns.ts с ИНН/КПП/ОГРН/ОКТМО/ОКВЭД/ОКФС/ОКОПФ/ОКПО/СНИЛС/СФР.
- ReportEditsBuilderService.build() → BuhotchEditsShape: дефолты из
  ledger2 + requisites + balance_corrections.
- buildInitialReportEdits резолвер с dirty-merge: defaults ⊕ editedFields
  из существующего drafта (applyDirtyOverrides по JSONPath).
- Рефактор BuhotchGenerator.generate(edits: BuhotchEditsShape) — чистая
  сериализация без ledger-логики (она теперь в EditsBuilder).
- generateReportFromEdits резолвер + XSD-валидация + запись в архив.
- Старый generateReport(data, organization) удалён полностью.
  ReportInput-shape оставлен временно для 6 non-BUHOTCH генераторов
  (переведутся на свои EditsShape в STORY-2-5/2-6). BUHOTCH-тесты
  генератора skip'нуты до переписи на edits.

Frontend:
- useReportDraft composable: load через buildInitialReportEdits,
  debounced autosave 500мс, dirty-tracking JSONPath'ами, regenerate/clear.
- BuhotchEditor.vue + BalanceRowEditor.vue — editable reference-форма:
  v-model:edits, @dirty, q-input rules по XSD-regex. Старый BuhotchForm.vue
  оставлен для post-generation XML-preview (заменится в STORY-2-4).
- reportStore: старый generate(data, org) удалён → новые методы
  buildInitialEdits / getDraft / saveDraft / deleteDraft /
  generateFromEdits; DocumentsPage временно использует fast-path
  buildInitialEdits → generateFromEdits до STORY-1-7/STORY-2-4.

SDK:
- generateReport.ts удалён.
- Новые мутации: generateReportFromEdits, saveReportDraft, deleteReportDraft.
- Новые queries: buildInitialReportEdits, getReportDraft, listReportDrafts.
- Новые selectors: reportDraftSelector, buildInitialReportEditsSelector.
- schema.gql + Zeus регенерированы (52 класса резолверов).

bmad:
- components/context/bmad/reports-editable-forms/ — config + sprint-status.yaml
  c 17 сторями по 3 спринтам; Sprint 1 закрыт.

Typecheck + vue-tsc чисты. XSD-тесты генераторов (кроме BUHOTCH) остаются
актуальными через legacy ReportInput path.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:43 +00:00
coopops 84bc1ed558 [989-8][@ant] fix(reports): скачивать ФНС-XML реально в windows-1251
XML генераторов ФНС объявлял encoding="windows-1251", но Blob в браузере
писался utf-8. Контур/СБИС выдавали предупреждение «объявлена windows-1251,
фактическая UTF-8» при загрузке файла.

Теперь перед скачиванием проверяем пролог: если cp1251 — перекодируем
JS-строку в байты cp1251 через пакет `windows-1251`. Для СФР-ЕФС-1 (utf-8)
оставляем как есть. Байты теперь физически совпадают с объявленной
кодировкой.
2026-04-23 13:30:43 +00:00
coopops 5500d580f4 [989-8][@ant] chore(reports): регенерация schema.gql + SDK после мёрджа dev
После merge origin/dev подтянулся фикс генератора схемы (0c5e04a484),
который возвращает все 51 классы резолверов (было 8) и поле
can_edit_requirement в permissions.

Пересобран schema.gql явным `generate-schema`, далее `generate-client`
+ `sdk build`. Типы в SDK соответствуют runtime controller, tsc чист
и в desktop, и в controller.
2026-04-23 13:30:43 +00:00
coopops 52a7911ed5 [989-8][@ant] feat(reports): клиентский экспорт формы в PDF + убрать пустой PDF-бланк и XSD из UI
Бухгалтеру нужен заполненный документ для просмотра, а не пустой бланк.
Раньше кнопка «PDF» скачивала печатную форму без данных — бесполезно;
XSD вообще не нужен ни председателю, ни бухгалтеру.

Стало:
- html2pdf.js конвертирует отрендеренную `.printable-form` (Vue) в PDF на
  клиенте. Две кнопки в диалоге: «Для отправки (XML)» + «Для просмотра
  (PDF заполненный)»
- Имя файла: <тип>-<год>[-q<период>].pdf

Удалено мёртвое:
- Backend: ReportStandardsService + downloadReportXsd/BlankPdf резолверы +
  DTO ReportXsdFile/ReportBlankFile
- SDK: queries/selectors для тех же
- Frontend: downloadXsd/downloadBlankPdf из store/api/types
- Бланки в components/reports-standarts/ остались как референс
  разработчика формы — переформулировано в README
2026-04-23 13:30:42 +00:00
coopops 83f2d69cd6 [989-8][@ant] feat(reports): полноценная вёрстка всех 6 форм + UX-правки диалога
UI-правки:
- Убрана кнопка «Скачать XSD» — бухгалтер/председатель её не используют
- Две кнопки: «Для отправки (XML)» и «Для просмотра (PDF)»
- Удалён метод downloadXsd из Report store (api/types остались — резолвер
  на бэке может пригодиться для QA)

Инфраструктура форм:
- useReportXml.ts — общий composable: парсер XML через DOMParser +
  базовая шапка + helper'ы (getAttr, getNum, getByLocal для namespace-
  тегов ЕФС-1, padInn, formatDate, fmt/fmtZero)
- _printable-form.scss — общий стиль A4-бланка: Times New Roman, рамки,
  штрихкод-заглушка, ячейки ИНН, .data-table, подпись. Подключается через
  @use в scoped-стиль каждого SFC
- Удалён FormStub.vue — больше не нужен, все формы полноценные

Полноценная вёрстка:
- BuhotchForm — рефакторинг на useReportXml + shared scss
- DusnForm — титул + раздел 1.1 (сумма к уплате) + 2.1.1 (расчёт по
  объекту «доходы») из <УСН> в XML
- Ndfl6Form — титул + раздел 1 (КБК, сроки 1-6) + раздел 2 (ставка,
  исчислено/удержано/возвращено)
- RsvForm — титул + раздел 1 (сводка ОПС/ОМС/ВНиМ). Для нулевого отчёта
  блок РасчетСВ пуст, явно показываем это пометкой
- PsvForm — титул + раздел 3 с таблицей персон (ФИО/СНИЛС/сумма выплат)
- UusnForm — единый лист с атрибутами <УвИсчСумНалог> + маппинг кодов
  периода (21/31/33/34 → название квартала)
- Efs1Form — раздел 2 СФР с подразделами 2.1 (тариф, база, исчислено) и
  2.3 (СОУТ). Парсит namespace-теги через localName

README widgets/report-forms: статус форм без stub-пометок, описание
composable + shared scss, правила работы (от бланка к XML).

Закрывает UX-запрос: бухгалтер видит формы «как документ», XML только на
скачивание, без raw-XML в UI.
2026-04-23 13:30:42 +00:00
coopops eebd1d6368 [989-8][@ant] chore(desktop): алиас extensions/* через quasar build.alias
Было: `import from 'extensions/reports/...'` падал в vite с «Failed to
resolve import», хотя tsc прошёл — paths/alias не совпадали между
tsconfig и vite. Сборка ловила ошибку, но долго.

Стало: `build.alias = { extensions: ./extensions }` в quasar.config.cjs.
Quasar CLI сам пробрасывает его и в `viteConf.resolve.alias`, и в
автогенерированный `.quasar/tsconfig.json` paths. Теперь `tsc`, `vue-tsc`,
IDE и Vite видят одно и то же — ошибка импорта ловится сразу в
typecheck, без полной сборки.
2026-04-23 13:30:41 +00:00
coopops 730e83d44d [989-8][@ant] feat(reports): PDF-бланк РСВ + заготовки Vue-форм для всех отчётов
- РСВ: конвертирован 20-страничный TIF в PDF (bilevel CCITT G4, ~700 KB),
  удалён дубликат 1151111_5.08000_11_1.tif, добавлен в PDF_BLANK_MAP
- FormStub.vue — базовая форма-заглушка: шапка со штрихкодом, ячейки ИНН,
  ОКВЭД/ОКПО/ОКТМО, блок «в разработке», раскрываемый исходный XML
- Заготовки форм для всех отчётов: DusnForm, Ndfl6Form, RsvForm, PsvForm,
  UusnForm (та же форма для UV_VZNOSY), Efs1Form — все делегируют FormStub
  с правильными title/КНД/ВерсФорм. Заполнять по мере готовности
- ReportPreviewDialog: статичная мапа reportType→компонент, fallback
  textarea заменён на «нет данных»
- README в widgets/report-forms/ — статус форм, архитектура,
  инструкция «как перевести stub → полноценную форму»
- README reports-standarts: документирована конвертация TIF→PDF для РСВ
  (snippet Python с пояснением почему bilevel, не RGB) + правило sync
  PDF_BLANK_MAP ↔ PDF_AVAILABLE
2026-04-23 13:30:41 +00:00
coopops 94af623ee0 [989-8][@ant] feat(reports): визуальный превью отчётов + скачивание XSD/PDF-бланка
- Backend: ReportStandardsService отдаёт XSD (cp1251→utf-8) и PDF-бланк
  из components/reports-standarts/ с маппингом ReportType→папка→файл
- Резолверы downloadReportXsd и downloadReportBlankPdf (Query, chairman-only)
- DTO ReportXsdFile{content,fileName}, ReportBlankFile{content,fileName,mimeType}
- SDK: новые queries + selectors под obe формы, регенерирован zeus
- Frontend: методы useReportStore.downloadXsd/downloadBlankPdf c триггером
  download в браузере (blob→a.click)
- Reference-форма BuhotchForm.vue: 2 листа (титул КНД 0710096 + баланс
  ОКУД 0710001) с вёрсткой «как документ» — Times New Roman, A4, рамки,
  штрихкод-заглушка, ячейки ИНН. Парсит XML через DOMParser, шапку
  fallback-ом из requisites
- ReportPreviewDialog.vue заменяет ReportResultDialog: полноэкранный
  диалог, слева форма-бланк, справа панель Скачать XML/XSD/PDF.
  Для не-BUHOTCH форм пока fallback textarea с исходным XML
- Удалён старый ReportResultDialog.vue

Закрывает issue 989-8.
2026-04-23 13:30:41 +00:00
coopops 22f18a63ec [989-7][@ant] docs(reports-standarts): добавить бланки упрощённой бухотчётности (0710096) и актуальной ЕФС-1, README папок
- Бухбаланс/: TIF + PDF бланка КНД 0710096 ВерсФорм 5.04 (упрощённая
  бухотчётность НКО по 66н, приложение №5) — совпадает с генератором
  buhotch.generator.ts и эталоном NO_BOUPR_romashka.xml
- Бухбаланс/: xls с образцами упрощённых форм баланса/ОФР/ОЦС —
  референс для будущей вёрстки формы в UI
- 4ФСС-ЕФС-1/: актуальный бланк ЕФС-1 (приказ СФР от 17.11.2025 №1462),
  соответствует XSD efs1.xsd с targetNamespace 2026-01-01
- УУСН/: распакованный бланк КНД 1110355 (Уведомление об исчисленных суммах)
- Новый README в components/reports-standarts/ с картой форм и правилами
  синхронизации XSD↔DTO
- Поправлен README tests/fixtures/reports-references/: эталоны Восхода
  удалены, Ромашка — обезличенный структурный аналог
2026-04-23 13:30:40 +00:00
coopops 18712aa83f [989-7][@ant] feat(reports/settings): маска ввода для рег.номера СФР и СНИЛС
RequisiteField теперь принимает опциональные props mask/fillMask и прокидывает
их в q-input. SettingsPage:
- Рег. номер СФР: mask='###-###-######' → вводится как XXX-XXX-XXXXXX
- СНИЛС подписанта: mask='###-###-### ##' → XXX-XXX-XXX YY

Формат совпадает с @Matches в DTO и XSD ФНС/СФР — бухгалтер набирает «как
видит», backend принимает без ручной нормализации.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:40 +00:00
coopops 73c37ec4ab [989-7][@ant] fix(reports): все DTO реквизитов выровнены под XSD ФНС
Проверил OrganizationDataInputDTO и UpdateReportRequisitesInputDTO против
паттернов XSD (NO_BUHOTCH / NO_USN / …). До этого UpdateReportRequisitesInput —
полей manual-ввода — валидировал только @IsString: сохранялись любые значения
(ОКТМО 10 цифр, ОКПО 11-13 и т.д.), а XSD на выгрузке падал. Теперь оба DTO
применяют единые regex:

  ИНН   — 10 (юр) или 12 (ИП) цифр        \d{10}|\d{12}
  КПП   — 4 цифры + 2 [0-9A-Z] + 3 цифры  \d{4}[0-9A-Z]{2}\d{3}
          (5-6 позиции могут быть буквами — иностранные организации)
  ОГРН  — 13 или 15 цифр                  \d{13}|\d{15}
  ОКТМО — 8 или 11 цифр                   \d{8}(\d{3})?
  ОКВЭД — XX, XX.X, XX.XX, XX.XX.X/XX     \d{2}(\.\d{1,2}){0,2}
  ОКФС  — 1-3 цифры                        \d{1,3}
  ОКОПФ — 5 цифр                           \d{5}
  ОКПО  — 8 или 10 цифр                    \d{8}(\d{2})?
  СНИЛС — XXX-XXX-XXX YY или 11 цифр       \d{3}-\d{3}-\d{3} \d{2}|\d{11}
  РегСФР— XXX-XXX-XXXXXX (14 симв.)        \d{3}-\d{3}-\d{6}

SettingsPage: placeholder ОКТМО «8 или 11 цифр».

Источник истины — XSD отчётности. При изменении XSD обновляем паттерны
здесь, а не наоборот.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:40 +00:00
coopops e6812c01e2 [989-7][@ant] fix(reports): валидация ОКПО соответствует XSD ФНС (8 или 10 цифр)
Было: UpdateReportRequisitesInputDTO.okpo и OrganizationDataInputDTO.okpo —
@IsString без паттерна/длины → сохранялись любые значения (11-13 цифр),
при генерации отчёта XSD падал «[facet 'pattern'] not accepted by [0-9]{10}».

Стало: @Matches(/^\d{8}(\d{2})?$/) — принимаем 8 (ГОСТ-юрлицо) или 10 (ФНС).
Сообщение «ОКПО — 8 или 10 цифр». SettingsPage: placeholder «10 цифр».

Главный контракт для поля — валидация XSD отчётности (согласование с ФНС),
UI-сохранение подгоняется под неё.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:40 +00:00
coopops 05688b82d0 [989-7][@ant] fix(reports): SettingsPage getSource через Zeus.RequisiteSource (не хардкод)
Использую enum из SDK Zeus — он генерируется из schema.gql при каждой пересборке,
всегда синхронен с backend. Захардкоженные 'database'/'manual' были time-bomb
(при переименовании enum-values на бэке UI молча переставал работать).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:40 +00:00
coopops 858a74a507 [989-7][@ant] fix(reports): реквизиты — badge «Не заполнено» везде + generateReport class-validator ошибки
Проблема: бухгалтер на странице «Реквизиты отчётности» видел badge «Не заполнено»
у каждого поля, хотя данные заполнены и отображаются. При генерации любого отчёта
падал BadRequest с class-validator сообщениями «inn should not be empty, inn must
be a string, КПП должен быть 9 цифр, ...».

Причины:
1. UI: Nest сериализует enum RequisiteSource ключами GraphQL (DATABASE/MANUAL/EMPTY),
   а getSource() в SettingsPage сравнивал с TS-значениями (database/manual/empty) —
   всегда попадал в 'empty' → badge «Не заполнено». Фикс: toLowerCase-нормализация.
2. Backend: OrganizationDataInputDTO — опциональный override при generateReport,
   но поля inn/kpp/orgName/ogrn/okved/oktmo/signerLastName/signerFirstName были
   помечены @IsNotEmpty. Когда клиент не передавал organization, NestJS pipe всё
   равно валидировал DTO и ругался на пустые required-поля. Фикс: все поля → IsOptional
   + nullable=true; паттерн-валидация применяется только если поле передано явно.
3. schema.gql / SDK регенерированы под nullable.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:40 +00:00
coopops 776c9770c3 [989-7][@ant] fix(reports): «Выпуск» без скобок + умеренный цвет Активный/Пассивный и Дебет/Кредит
- wallet-registry: id=0 → «Выпуск» (убрал отсебятину «(внешний источник)»)
- AccountsPage основная таблица: «Активный» blue-grey-8, «Пассивный» brown-7 + medium weight — не кричаще, но читаемо
- AccountsPage child-table: Дебет blue-grey-8, Кредит brown-7 — та же цветовая пара для консистентности

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:39 +00:00
coopops 5603106730 [989-7][@ant] fix(reports): убрать неиспользуемую displayAccountCode
Функция стала мёртвой после перехода Проводок по счетам на AccountIdCell
(accountCode вычисляется прямо в accountRows через /1000). Eslint
no-unused-vars ругался — удаляем.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:39 +00:00
coopops 1f23a27c6c [989-7][@ant] feat(reports): реестр счетов + AccountIdCell + wallet_id=0 «Выпуск», упрощение палитры
Shared
- wallet-registry: +{id:0, 'Выпуск (внешний источник)'} — frontend-only (в wallets.hpp нет), для walletop issue/consume где wallet_from=0 или wallet_to=0
- account-registry: TS-копия LEDGER2_ACCOUNT_MAP из accounts.hpp (04/08/51/58/80/86) + getAccountName/getAccountMeta/storedIdToCode
- AccountIdCell: EntityIdBadge + tooltip с названием счёта, принимает code (51), не stored id×1000

OperationsPage
- «Проводки по счетам» используют AccountIdCell: debitCode/creditCode через /1000

AccountsPage
- Основная таблица: id счёта через AccountIdCell (tooltip с названием)
- Убрана цветная q-badge «Активный/Пассивный» → text-caption.text-grey-7
- Child-таблица: «Дебет/Кредит» не позитивным/негативным, а серым (text-grey-8) — убрали разноцветие

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:39 +00:00
coopops d36e3f5bf2 [989-7][@ant] refactor(reports): подсветка expand-таблиц, tooltip кошельков, переходы к операции
- q-card flat bordered обрамляет таблицы «Движения»/«Проводки» в expand — тема подхватывается Quasar автоматически
- WalletIdCell: tooltip вынесен наружу EntityIdBadge (у badge нет default slot, tooltip внутри выпадал) — теперь подсказка с названием кошелька появляется при наведении
- AccountsPage: кнопка «Все проводки» → «Все операции»
- AccountsPage expand: колонка «открыть» — икона «fa-up-right-from-square» на каждой строке debit/credit, ведёт на OperationsPage?process_hash=…; убран цветной q-badge по типу — просто text-positive/negative
- WalletsPage expand: такая же икона «Показать операцию» на каждой строке движения
- OperationsPage: поддержан route.query.process_hash — фильтр применяется в loadHistory, chip «Операция xxxxxxxx» активного фильтра (removable → чистит URL)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:39 +00:00
coopops c9213c58e3 [989-7][@ant] refactor(reports): UX экспанда — EntityIdBadge+tooltip, col-md-6 таблицы, чистая шапка
Shared
- src/shared/lib/ledger2/wallet-registry.ts: 17 пар id→name (sync с contracts/cpp/lib/core/ledger2/wallets.hpp) + getWalletName()
- extensions/reports/shared/ui: WalletIdCell (EntityIdBadge + tooltip с названием из реестра, clip по клику), DirectionCell (стрелка + «Входящий/Исходящий/Перевод» одним текстом)

OperationsPage
- Колонка № = EntityIdBadge[:8] + tooltip; клик копирует полный processHash
- Chip операции flat: pastel bg + deep text по префиксу action_code, без иконки/outline
- Шапка expand переделана: цветная вертикальная полоска (accent по префиксу), крупное название, action_code моно, ID процесса через EntityIdBadge полный, примечание с иконкой note-sticky
- Таблицы «Движения» и «Проводки» в .row.q-col-gutter-md → col-12.col-md-6 (стек на мобилках)
- «Проводки по счетам»: убраны q-badge зелёный/красный — просто моноширинный текст
- Движения используют DirectionCell + WalletIdCell

WalletsPage expand — тот же DirectionCell + WalletIdCell.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:39 +00:00
coopops 8a55b3b1f4 [989-7][@ant] fix(reports): SQL-каст global_sequence::bigint + Из/В стрелки в expand WalletsPage
- typeorm-ledger2-state: global_sequence хранится как varchar(32), COALESCE с bigint падал «types text and bigint cannot be matched» — явный ::bigint каст на обеих сторонах сравнения и в MIN()
- WalletsPage expand: child-таблица движений теперь с колонками Из/В, стрелка ↓ входящее / ↑ исходящее / ↔ перевод; собственный кошелёк (props.row.id) выделен жирным

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:39 +00:00
coopops aea781fa83 [989-7][@ant] feat(reports/ledger2): корректные проводки и движения — 2 таблицы со стрелками, id/1000, badgeId, 2-знака
Backend (controller):
- Ledger2Operation +walletFrom/walletTo (из data->>'wallet_from|wallet_to' для walletop)
- GetLedger2HistoryInput +parentApplyGlobalSequence: при раскрытии одного apply
  фильтруем siblings диапазоном global_sequence до следующего apply того же
  processHash — multi-effect процессы (cap.act2res) больше не сваливают трио
  соседних apply в одну кучу
- SDK перегенерирован

Frontend (desktop/reports):
- OperationsPage: колонка № = processHash[:8] как q-badge в моноширинной стилистике
- Строка операции: q-chip цвета по префиксу action_code (reg/wall/cap/mkt/sov/mig)
- Expand разделён на 2 таблицы:
  * «Движения по кошелькам» (walletop) со стрелками: ↓ зелёное входящее,
    ↑ красное исходящее, ↔ перевод; колонки «Из» / «В» / сумма
  * «Проводки по счетам» (debit+credit) парой Дт→Кт в одной строке; id/1000
    для счетов (51000 → 51)
- Суммы форматируются formatAsset2Digits (2 знака вместо 4): 100.0000 → 100,00
- Загрузка siblings через parentApplyGlobalSequence — пары Дт/Кт не разваливаются
- AccountsPage / WalletsPage: формат суммы 2 знака в child-таблицах

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:39 +00:00
coopops 8917dbe392 [989-7][@ant] refactor(desktop/FSD): вывести api за фасад model в Ledger2/Report/Account
- entities/Ledger2: добавлен Pinia store (loadAccounts/loadWallets/loadHistory + getAccountById/getWalletById), api/ теперь внутренний (move api.ts → api/index.ts), index.ts экспортирует только model + types
- entities/Report: убран export api из index.ts, store расширен loadRequisites/updateRequisites/checkReadiness
- entities/Account: добавлен прямой реэкспорт model (к легаси namespace ExtensionMode)
- 4 reports-страницы переведены на useLedger2Store()/useReportStore()/useAccountStore() — никакого прямого *Api в страницах

Эталон — entities/Meet. Смысл — публичный контракт entity = только model, чтобы позже её можно было упаковать в виджет/расширение.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:38 +00:00
coopops 9eaa0fab4c [989-7][@ant] fix(reports): видимый чип фильтра на OperationsPage + убрать hero-title на DocumentsPage/SettingsPage
- OperationsPage: chip «Счёт NN — Название» / «Кошелёк NN — Название» при переходе с Wallets/Accounts, removable синхронизирует URL query
- DocumentsPage: убран hero-card «Отчётность»
- SettingsPage: убран hero-card «Реквизиты отчётности»

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:38 +00:00
coopops 3581815f3d [989-7][@ant] fix(reports): тёмная тема date-пикеров, фильтр по кошельку/счёту, заголовок на AccountsPage
- OperationsPage: нативные q-input type=date → q-popup-proxy + q-date (тема + иконка корректны на dark)
- ledger2 getHistory: фильтр accountId для apply-заголовков через подзапрос по process_hash — переход «К операциям»/«Все проводки» теперь находит связанные apply; siblings (walletop/debit/credit) остаются на прямом совпадении
- AccountsPage: убран hero-title «Счета» (как для OperationsPage)
- регенерирован SDK под новое поле processHash в schema.gql

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:38 +00:00
coopops a17bead082 [989-7][@ant] fix: убрать заголовок и дублирующий код операции на OperationsPage — русское название операции достаточно, технический код захламляет интерфейс бухгалтера 2026-04-23 13:30:38 +00:00
coopops f14296d468 [989-7][@ant] fix: добавить ?? [] для childOps.get() — vue-tsc: Map.get() может вернуть undefined, rows требует массив 2026-04-23 13:30:38 +00:00
coopops dabba3235a [989-7][@ant] fix: переработать UI расширения reports и исправить баги данных — бухгалтер не мог пользоваться интерфейсом из-за технических меток и сломанной генерации
- убраны hero-subtitle на всех страницах (Операции, Кошельки, Счета, Отчётность, Реквизиты)
- OperationsPage: только apply-записи, реестр ACTION_CODE → русское название, FIO-обогащение, дочерние проводки в expand
- WalletsPage/AccountsPage: inline-expand с движениями/проводками без перехода на другую страницу
- SettingsPage: убрана секция «Готовность форм», кнопка сохранения наверх, фикс бейджа (source database→blockchain)
- DocumentsPage: русские названия форм (BUHOTCH→Бухотчётность и т.д.)
- backend: фикс quantity (amount вместо quantity), wallet_from/wallet_to в фильтре accountId, новый processHash-фильтр
- SDK: processHash добавлен в GetLedger2HistoryInput
- Report/api.ts: organization не отправляется как undefined (фикс class-validator ошибок)
2026-04-23 13:30:38 +00:00
coopops 214db313cc [989-4][@ant] fix(extensions): reports как default app + initialize-стаб — устанавливается автоматически
Два пробела после [116] «reports встроенный extension»:
- reports отсутствовал в getDefaultApps(), поэтому не оседал в postgres через installDefaultApps на старте controller'а — приходилось ставить руками.
- ReportsExtensionModule не имел метода initialize(), и lifecycle-service кидал «moduleInstance.initialize is not a function» при runApp.

Фиксы:
- getDefaultApps(): +reports (enabled=true, builtinDefaultConfig).
- ReportsExtensionModule: async initialize() {} — stub по образцу BuiltinPluginModule (нет своего крона/состояния).
- postgres-init.ts: дублирующий seed в initExtensionsInPostgres (ON CONFLICT DO NOTHING) — чтобы boot:extra сразу давал столу появиться, не ждать следующего onModuleInit.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops 425b3884d0 [989-4][@ant] fix(desktop): vue-tsc зелёный в PaymentCard — каст payment.id к string
Zeus-скаляр ID разворачивается как непрозрачный `{}`, поэтому `:id='payment.id'`
не присваивался string-пропу кнопок. Явный `String(payment.id)` убирает обе ошибки
vue-tsc без изменения runtime-поведения (v-if уже гарантирует truthy).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops 84b051bbe9 [989-4][@ant] fix(controller): typecheck зелёный — pre-existing импорты и делегаты
- `appstore/extension/extension-app.module.ts` — `./interactors/*` → `../interactors/*` (файлы лежат в `application/appstore/interactors/`, модуль в соседнем `extension/` подкаталоге).
- `gateway/adapters/gateway-interactor.adapter.ts` — адаптер реализует `GatewayInteractorPort`, но не прокидывал два метода. Добавлены делегаты `executeIncomePayment(id, status)` и `expireOutdatedPayments()` в `GatewayInteractor` (сами методы уже реализованы в интеракторе — adapter просто их вызывает).
- `app.ts` — явная аннотация `const app: Express = express()` — иначе inferred-тип ссылается на внутренний путь `@types/express-serve-static-core` из pnpm-store (TS2742 portability warning).

`tsc --noEmit` теперь зелёный. Runtime поведение не меняется.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops 4d56683fc6 [989-4][@ant] refactor(capital): COMMIT_RID перенесён в approvecmmt — отдельный процесс cap.apprvcmmt
По ревью 2026-04-20 (#3112334605): коммит РИД — самостоятельная фаза жизненного цикла
(Dr 08 / Cr 80 на каждом одобрении мастера), acceptance в signact2 только закрывает
накопленное 08 на 04. Matrix 2026-04-19 (Ангелина): «собирать на 08 частями по мере
коммитов, переносить на 04 когда РИД собран».

Изменения:
- `capital::approvecmmt` — после `upsert_creator_segment` считает
  Δ `segment.available_for_program` (intellectual_cost − debt_amount) и эмитит
  `COMMIT_RID` на эту дельту с `process_hash = project_hash`. Инвариант
  `delta >= 0` защищён `eosio::check`.
- `capital::signact2` — `COMMIT_RID` больше не вызывается здесь; остаётся
  `ACCEPT_RID` на полный `segment.available_for_program` + опциональный
  `REPAY_LOAN`. Σ COMMIT_RID по сегменту == ACCEPT_RID → 08 закрывается в ноль.
- `process-hash-locator.ts` — новый process_type `cap.apprvcmmt` → table `projects`,
  field `project_hash`. `cap.commit` action_code перемаплен с `cap.act2res`
  на `cap.apprvcmmt`. `cap.act2res` теперь содержит только `cap.accept` + `cap.lnrepay`.
- `LEDGER2_CHART_OF_ACCOUNTS.md` + `_blago/17/req#50` — раздел «Процессы»
  обновлён: добавлен `cap.apprvcmmt`, переформулированы комментарии по
  `cap.commit` / `cap.accept`, зафиксирован инвариант.

Сборка capital.wasm / ledger2.wasm — зелёная.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops bd63c3884e [989-4][@ant] review(ledger2/reports): ответы на 29 комментариев PR #357 — расширение справочника, тонкий DocumentsPage со стором, blockchain→database в reports
- docs: _blago/17 req #50 — §2 переписан на текущее состояние (6 счетов, 17 кошельков, 5 WalletOp, 18 кодов) + запись 2026-04-20 merged. _blago/33 новый req «Реестр операций ledger2 для отчётности» (только таблицы).
- contracts: wallets.hpp — MARKETPLACE_FUND → «ЦПП Стол Заказов». table_ledger2_account.hpp — doxy формула сальдо ACTIVE/PASSIVE/ACTIVE_PASSIVE. LEDGER2_CHART_OF_ACCOUNTS.md — sync.
- cooptypes: ledger2/tables/ оформлены как capital/tables (accounts/wallets/meta с tableName+scope), interfaces/ledger2.ts — IAccount2/IWallet2/IMeta.
- controller: Ledger2Contract.contractName.production вместо 'ledger2'-хардкода (process-registry.service, typeorm-ledger2-state.repository, table-names через Ledger2Contract.Tables.*.tableName). HARD_LIMIT пояснён. V2.0.0/V2.0.1 миграции удалены (sync: true). reports → builtin extension. chart-of-accounts.entity: убран TODO LONG_TERM_LOANS. ledger2-account/wallet interfaces — ACTIVE_PASSIVE явно задокументирован, sink заменён на конкретные назначения.
- controller/reports: RequisiteSource BLOCKCHAIN → DATABASE (ИНН/КПП/ОГРН живут в БД кооператива, не в контракте); preview — КНД-коды помечены как национальный стандарт ФНС; resolver — убраны лишние уточнения в description; xml-utils — generateUuid удалён, psv/uusn/uv-vznosy переведены на generateFnsFileName. AGENTS.md — раздел «Process Registry — обязательные инварианты» + feedback в memory.
- desktop: DocumentsPage.vue разбит на тонкий компонент + GenerateReportDialog / ReportResultDialog; Pinia-store useReportStore (entities/Report/model/) владеет reports/archive/downloads. WalletsPage — чистая таблица без soviet/пулов. OperationsPage — querySelector → Vue refs, Memo→Заметка. Notify.create → SuccessAlert/FailAlert из shared/api.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops 7bbce2298d [989-4][@ant] fix(test): AC8 в ledger2-migrate.test.ts — учесть baseline кошельков
Первый прогон показал: Σ wallets после миграции = 1_000_182_700 (testnet
накопил wallet-балансы при boot процессе создания 5 пайщиков), но AC8
ожидал ровно seedCash=5000. Это моя ошибка в ассерте — seed добавляет
seedCash к baseline, а не формирует всю сумму.

Фикс:
- Добавлена переменная baselineWalletsTotal (измеряется в seed-фазе ДО
  первой миграции, как и baselineCashAcc/ShareAcc/EntryAcc).
- AC8 теперь проверяет totalWallets ≈ baselineWalletsTotal + seedCash.

Прогон полного pnpm test:all после фикса: 76 passed | 3 failed | 1 skipped.
Все 3 оставшихся fail — pre-existing, не связаны с ledger2-рефактором:
- registrator тесты ждут legacy `circulating_account`, отключённый ещё в
  Epic 1 intro (b67d41b00f).
- capital-import тест на `status === 'active'` — логика importcontr.cpp
  не менялась в этом PR.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops b17ddb46a8 [989-4][@ant] fix(ledger2): миграция progwallets — прямой emplace в wallets2 без бух-проводок
Первый прогон тестов обнаружил архитектурную ошибку моей предыдущей
реализации миграции: я предположил, что `progwallet.blocked` в soviet —
это часть `legacy::ledger::accounts[80]` и поэтому при переносе вычитал
progwallet-суммы из share_money. Тестнет показал обратное:

  Error: share_remain < 0 на voskhod
    (share_money=3500 RUB, blagorost_invest=1 млрд RUB)

`legacy::ledger::accounts` и `soviet::progwallets` — параллельные системы
учёта, `progwallets.blocked` НЕ проводится через 80-й счёт. Любая бух-
проводка при переносе progwallet давала бы двойной учёт на 80.

Фикс:
- Удалены из actions.hpp записи `mig.blago` (TRANSIT_BLAGOROST) и
  `mig.commit` (TRANSIT_COMMITMENT) — они были ошибкой. Осталось 18 ops.
- `migrate.cpp` разделён на два независимых потока:
  A. Бухгалтерский — 4 inline apply(TRANSIT_*) по legacy::accounts
     (min_share + share + entry + rid). Формулы упрощены:
     share_money = cash_legacy − entry_legacy,  rid_share = share_legacy − share_money.
  B. Программные кошельки — новый хелпер `emplace_wallet_only()`,
     ПРЯМОЙ wallets2.emplace для blagorost (9001) и generator (10001)
     БЕЗ ledger2::apply и БЕЗ Dr/Cr. progwallets не влияют на 80/86/04.
- Инварианты упрощены: share_remain < 0 проверка убрана (невозможен), но
  остались cash_legacy >= entry_legacy и share_legacy >= share_money.

process-hash-locator.ts: убраны `mig.blago` и `mig.commit` из маппинга
action_code → process_type. `mig.transit` остался с 4 action_code.

Документация LEDGER2_CHART_OF_ACCOUNTS.md обновлена: раздел миграции
разделён на A (4 проводки через apply) и B (2 прямых emplace без проводок).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops 7d9e06e24d [989-4][@ant] refactor(ledger2): apply.cpp использовать get_cooperative_or_fail + справочник LEDGER2_CHART_OF_ACCOUNTS.md
- apply.cpp: ручной cooperatives2_index.find → get_cooperative_or_fail из
  lib/domain/table_registrator_coops.hpp. Хелпер проверяет существование,
  is_cooperative и status='active' единым check'ом. Закрывает коммент
  ревью 3110497427 PR #357.

- Добавлен components/context/notes/LEDGER2_CHART_OF_ACCOUNTS.md — полный
  справочник «как заполняются по факту»: план счетов (6), кошельки (17),
  типы WalletOp (5 включая WALLET_ONLY), реестр операций (20 записей с
  Dr/Cr/Wallet/назначением), связь process_type → action_code, инварианты
  миграции. Закрывает коммент 3111229308 PR #357.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops c2e2e51e27 [989-4][@ant] refactor(ledger2): пересмотр плана счетов + кошельков + реестра операций по code-review PR #357
Ответ на 22 треда ревью владельца (2026-04-20). Детерминированная миграция
без транзитного 99 и зеркала CASH_MAIN, разнесение legacy на 6 целевых
кошельков. Разделение ACT2_SHARE на commit (08/80) + accept (04/08).
Заём переведён с 67 на 58/51. Введён WALLET_ONLY тип проводок.

План счетов (6 вместо 7):
- удалён 99 OPENING_TRANSIT (лишний транзит)
- удалён 67 LONG_TERM_LOANS (займы теперь через 58/51)
- добавлен 08 NON_CURRENT_INVESTMENTS «Вложения во внеоборотные активы»
  для промежуточного «принятый коммит»: commit → Dr 08/Cr 80, accept → Dr 04/Cr 08

Кошельки (17 вместо 11):
- удалены: 1001 CASH_MAIN, 4050 LOAN_RECEIVED, 4052 DEBT_CLOSED_SINK
- добавлены: 4051 LOAN_ISSUED, 5001 MANUAL_ADJUST,
  9001-9004 Благорост (INVEST/RID/PROPERTY/MEMBERSHIP),
  10001-10002 Генератор (COMMIT/MEMBERSHIP), 11001 MARKETPLACE_FUND

Реестр операций (20 записей, WalletOp::WALLET_ONLY=4 новый):
- ACT2_SHARE разбит на COMMIT_RID (cap.commit) + ACCEPT_RID (cap.accept)
- ACT2_LOAN/LOAN_REPAYMENT → ISSUE_LOAN (cap.lnissue, Dr 58/Cr 51) + REPAY_LOAN (cap.lnrepay, Dr 80/Cr 58)
- CAPITAL_IMPORT → ISSUE на BLAGOROST_INVEST 9001
- ACT2_PROGRAM_PROP → ISSUE на BLAGOROST_PROPERTY 9003
- CONVERT_TO_AXN → human_name «Трансляция паевого взноса из ЦПП Цифровой Кошелёк в членский взнос за пользование инфраструктурой»
- Новое cap.invest — WALLET_ONLY TRANSFER SHARE_FUND_PAY 2001 → BLAGOROST_INVEST 9001 (без бух-проводок)
- OPENING_CASH удалён. OPENING_SHARE/ENTRY/RID → TRANSIT_SHARE/ENTRY/RID
- Добавлены TRANSIT_MIN_SHARE, TRANSIT_BLAGOROST, TRANSIT_COMMITMENT
- Compile-time валидации: wallet_only_has_zero_accounts, dr_ne_cr_when_posting, transfer_wallet_from_ne_to (покрыт и WALLET_ONLY)

Миграция (migrate.cpp) — вариант C + progwallets:
- Читает cooperative2.minimum + active_participants_count (fallback — participants status='accepted')
- Суммирует progwallet.blocked по program_id=4 (Благорост) и =3 (Генератор)
- До 6 TRANSIT_* проводок per кооп с инвариантами eosio::check
- Прямые Dr/Cr без 99-транзита, двойной wallet-учёт исключён

Вызывающие контракты:
- capital::signact2: ACT2_SHARE → COMMIT_RID + ACCEPT_RID (атомарно, один process_hash). ACT2_LOAN → REPAY_LOAN
- capital::debtpaycnfrm: LOAN_REPAYMENT → ISSUE_LOAN (уточнено: это выдача займа, не возврат)

Controller + SDK:
- process-hash-locator.ts: мапа action_code → process_type под новые имена, до 3 action_code на один cap.act2res (commit + accept + lnrepay)
- sdk/reports/index.ts:4 — ИНН/КПП/ОГРН формулировка «живут в БД кооператива, не в блокчейне»

Тесты:
- ledger2-migrate.test.ts: переписан под 6 TRANSIT_* (AC1-AC9), проверка отсутствия 99 и 1001, инвариант Σ wallets
- ledger2-read-layer.test.ts: убран WALLET_CASH_MAIN, ACCOUNT_TRANSIT → проверка отсутствия, actionCodes 'mig.share'

Терминология:
- везде «паевой взнос» (не «пай», не «минимальный пай»). Feedback memory зафиксирован.

Закрытые треды ревью PR #357:
3110497427, 3110515593, 3110525276, 3110554221, 3110809387, 3110820659,
3110826179, 3110830707, 3110835085, 3110846530, 3110859570, 3110860470,
3110866644, 3110869995, 3110875784, 3110881945, 3110889550, 3110893784,
3110900719, 3110901751, 3111175626, 3111208865, 3111224738, 3111229308,
3111336184.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops 382f37b103 [989-4][@ant] revert(soviet): вернуть scope=_provider в converttoaxn Ledger2::apply (откат моего ошибочного Decision #7 из 42e9b536c8) + whitelist идентификаторов в migration V2.1.0
Файл converttoaxn.cpp
----------------------
Возвращаем код к состоянию из Epic 1 intro `b67d41b00fa`:
  Ledger2::apply(_soviet, _provider, CONVERT_TO_AXN, amount, coopname, process_hash, memo);

Что и почему было сломано:
- В Epic 1 intro `b67d41b00fa` стоял корректный scope=`_provider` —
  ledger2-зеркало легаси-кошелька из строки 21 (там
  `Wallet::sub_available_funds(_soviet, _provider, coopname, ...)` тоже
  на `_provider`-scope). Ручное тестирование владельца прошло успешно.
- В code-review коммит `42e9b536c83` (Decision #7) я сам, без
  воспроизводимого бага, свопнул аргументы на `Ledger2::apply(_soviet,
  coopname, ..., _provider, ...)`, рассудив, что имя параметра
  `coopname` «должно» означать кооп. Сломал: ledger2::apply валидирует
  `cooperatives2_index` → username пайщика (то, что реально передаётся
  в `coopname`-field action'а, см. system.adapter.ts:42 и memo
  «от пайщика с username=...») там отсутствует → action упал бы с
  «Неизвестный coopname: <username>».
- Cursor Bugbot на PR #357 справедливо указал на это. Признаю:
  это я привнёс в предыдущем коммите, теперь откатываю.

Scope двойной записи ledger2 — тот же `_provider`, что и у легаси-кошелька;
инжекция AXN (строка 49) идёт на `coopname`-параметр — это не меняется.

Файл V2.1.0__process_registry_jsonb_indexes.ts
-----------------------------------------------
Cursor LOW: migration строил DDL через template-literal интерполяцию.
Сейчас значения — литералы рядом в коде, инъекции нет, но future-edit
с кавычкой в названии поля сломает SQL. Добавил whitelist `^[a-z0-9_]+$`
с throw при нарушении — чисто defensive.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops c212fd7692 [989-4][@ant] test(capital): покрыть отделённый regshare после [562-13] — apprvappndx больше не inline-вызывает regshare
После [562-13] da8c443625 допуск (apprvappndx) и регистрация доли (regshare) разведены на два отдельных действия: signAppendix добавляет project_hash в appendixes контрибьютора, но сегмент в проекте больше не создаёт автоматически. Тесты 3-х спеков отражали старый «автоматический» флоу и падали на `Сегмент пайщика не найден` и `capital_contributor_shares = 0`.

Починка — без ослабления ассертов:
- processRegShare.ts: хелпер над capital::regshare
- A) "вклады… зарегистрированы автоматически" → "регистрируем доли через capital::regshare отдельным действием": спек сам вызывает regshare с user_shares = balance, жёстко проверяет segment.is_contributor=1, capital_contributor_shares==balance, Σ сегментов == Σ балансов, total_capital_contributors_shares==то же
- B) новый спек "regshare идемпотентен" — покрывает upsert-семантику regshare.cpp
- C) "тест ВЫСОКОЙ ТОЧНОСТИ": после signAppendix добавлен regshare по балансу — сегменты существуют до rfrshsegment/commitToResult; ассерт totalSharePercent≈100% остался

Результат: 60 passed | 1 skipped (61) против 3 failed | 56 passed | 1 skipped (60) до правки. Никаких .skip / try-catch-swallow — тесты честно зелёные.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:37 +00:00
coopops 2e0eb9a2de [989-4][@ant] fix(stream-consumer): убрать silent-error swallow + XAUTOCLAIM pending re-delivery + XTRIM MINID по consumption — чтобы parser/controller не теряли события при burst'ах и рестартах, и Epic 4 ProcessRegistry работал end-to-end на живой цепочке
Silent-catch в blockchain-consumer ACK'ил сообщения даже при упавшем saveDelta —
данные терялись безвозвратно; wallet::deposits/candidates2 не доходили до PG.
Consumer использовал `consumer-${random}` — каждый рестарт плодил zombie
со своими pending. Parser XTRIM MAXLEN=1000 при burst'ах удалял свежие
сообщения до того, как controller их прочитывал. rows$.subscribe без
error-handler'а молча убивал весь поток парсера при WS-разрыве.

Controller (blockchain-consumer.service.ts + redis-stream.service.ts):
- processDelta/processAction: убран try/catch-log-only → ошибки бросаются
  до handleMessage, сообщение остаётся pending в группе для retry.
- processAction: убран setTimeout(3s) fire-and-forget → ACK теперь после
  фактического save, а не до него.
- consumerName: стабильное 'coopback-main' вместо random.
- onModuleInit: recoverOwnPending (XREADGROUP STREAMS 0) доигрывает свои
  pending после рестарта; reclaimStalePending (XAUTOCLAIM idle>5min)
  забирает pending у зомби-consumer'ов.
- Периодические: XAUTOCLAIM 1/min + XTRIM MINID <first-pending-id> 1/30s
  — Redis-память ограничена фактической consumption, не придуманным числом.

Parser (RedisNotifier + DeltaParser + ActionParser + config):
- publishEvent/publishDelta/publishFork: XTRIM убран (trim — роль consumer'а).
- REDIS_STREAM_LIMIT удалён из config.ts / .env-example / AGENTS.md.
- rows$.subscribe({next,error,complete}) вместо callback'а: ошибка/complete
  триггерят process.exit, docker по restart:unless-stopped поднимает заново.

Integration tests (components/boot/src/tests/, +382 строк):
- process-registry.test.ts (Epic 4 e2e): 5 кейсов — reg.regist 2×apply,
  wall.deposit, processes listing, hex-64 validation, 404 на unknown hash.
- ledger2-read-layer.test.ts (Story 1.23 e2e): 5 кейсов — on-chain↔
  GraphQL срез accounts/wallets/history + фильтры actionCodes/accountId.
- shared/apiClient.ts: login chairman (eosjs-ecc) + gql + waitUntil.

Проверка на живой среде после fix'а:
- XLEN notifications = 70 (раньше 1001 фиксированно или потеря при burst).
- pending=0, lag=0 — ни одного silent drop, XAUTOCLAIM очистил зомби.
- blockchain_deltas впервые содержит wallet::deposits=3 (было 0).
- 18/18 boot integration + 77/77 controller unit тестов зелёные.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:36 +00:00
coopops 62bb9bddbb [989-4][@ant] refactor(process-registry): code review Epic 4 — починить тесты, локатор, миграцию, unify cap.act2res
Все блокирующие находки code review.

CRITICAL
  tests/unit/process-registry: переписаны под текущую архитектуру.
  Epic 1 addendum удалил wjournal/journal, Phase A стал читать
  blockchain_actions, но тесты остались мокать deltaRepo с _ledger2
  якорями → 4 из 6 кейсов падали с NotFoundException. Commit message
  Epic 4 "67/67 passed" стал неверен. Теперь:
    - Phase A мокается через actionRepository (name='apply', action_code
      в data, process_hash в data);
    - Phase B — deltaRepo с правильными таблицами (candidates2, results,
      deposits, etc.);
    - processType выводится из ACTION_CODE_TO_PROCESS_TYPE (не из
      delta.value.process_type);
    - добавлены кейсы reg.regist (2 apply под одним hash) и mig.opening;
    - account: '_ledger2' → 'ledger2' (bug с переименованием eeb4d50).
  Результат: 8/8 ProcessRegistry-тестов зелёные, всего suite 77/77.

HIGH — PROCESS_HASH_LOCATOR: неверные имена таблиц/полей.
  Проверено по C++ контрактам:
    registrator::regs         → candidates2                 (field: registration_hash)
    capital::segments         удалена из локатора           (project_hash, не result_hash)
    capital::debts/result_hash→ debts (только для cap.debt, поле debt_hash)
    capital::properties       → pgproperties                (field: property_hash)
    marketplace::requests/request_hash → hash               (поле именно hash)
  Без этого getProcess для reg.regist/mkt.offereq/cap.act2*/cap.act2prp
  возвращал пустое delta_history — UI был пустым на главном use-case.

HIGH — cap.act2res унификация (пользовательское уточнение).
  Акт-2 это ОДИН процесс с ДВУМЯ эффектами (приём РИД в пай + погашение
  займа), а не два процесса. В C++ ACTION_REGISTRY оба action_code
  (cap.act2shr + cap.act2ln) уже указывают на CAPITAL_ACT2_RESULT =
  "cap.act2res". Backend теперь то же:
    - ACTION_CODE_TO_PROCESS_TYPE: cap.act2shr / cap.act2ln → cap.act2res;
    - PROCESS_HASH_LOCATOR: cap.act2res → [results] (segments/debts
      связаны через project_hash, не result_hash — не часть этого процесса);
    - IProcessType: заменили cap.act2shr | cap.act2ln на cap.act2res.
  UI при рендере process.actions видит два apply с разными action_code
  → группирует и показывает два эффекта раздельно внутри одной карточки
  процесса (discriminator = action.data.action_code).

HIGH — Migration V2.1.0: индексы были без LOWER() → планировщик не
  выбирал их, все getProcess упирались в seq-scan blockchain_deltas.
  Теперь все expression-индексы построены на LOWER(value->>'field')
  (совпадает с сервисным WHERE). Обновлены имена таблиц/полей согласно
  новому PROCESS_HASH_LOCATOR. coopname не в индексе — OR (scope/value)
  не покрывается одним expression-index, постфильтр дёшев (≤5 строк
  per hash). CONCURRENTLY не используется (DEV-стенд).

HIGH — listProcesses GROUP BY двоил мульти-операционные процессы.
  Было: GROUP BY action_code, hash, coopname — для reg.regist (entrfee+
  minshare) и cap.act2res (shr+ln) показывало по две строки, totalCount
  (COUNT DISTINCT hash) не совпадал с items.length.
  Стало: GROUP BY LOWER(hash), coopname; MIN(action_code) для вывода
  processType (у мульти-action процессов оба action_code маппятся в
  один type, так что MIN даёт корректный тип).

HIGH — Убрать N+1 per-row counts в listProcesses.
  Было: на каждую строку page 3 SQL (countActionsByHash +
  countDeltasByHash + countDocumentsByHash). 100 строк × 3 SQL на
  request → connection pool exhaustion под нагрузкой. Поля
  actionCount/deltaCount/documentCount удалены из ProcessSummary DTO
  и IProcessSummary interface. UI запрашивает getProcess(hash) при
  раскрытии конкретного процесса — там счётчики выводимы из
  actions.length/delta_history.length/documents.length.

Silent fixes:
  - LIMIT/OFFSET в listProcesses: параметризация через $n вместо
    литералов (безопасность + корректность при edge NaN).
  - compareByBlock: tiebreaker по global_sequence (BigInt) когда
    block_num + created_at совпадают — детерминированный порядок.
  - blockchain-consumer: строгая проверка непустой строки в
    value.coopname перед fallback на scope (пустой "" теряет дельту).
  - Удалён dead LEDGER2_ACTION_NAMES.
  - Устаревший комментарий ProcessRegistryDomainModule → blockchain_actions.
  - add-test-user.ts: cleos-подсказки обновлены с wjournal на
    candidates2/accounts2/wallets2.

Преднамеренно НЕ трогаю:
  - Cross-tenant coopname validation (E1): оставлено для federation.
  - Fork purgeAfterBlock (E6): вне scope Story 1.23, общесистемный
    вопрос для отдельной задачи.
  - Redis cache hardening (E9-E11): TTL 60s acceptable для MVP.
2026-04-23 13:30:36 +00:00
coopops 175d9f5e8e [989-3][@ant] feat(ledger2): Story 1.23 — read layer в controller — getLedger2Accounts/Wallets/History + переключить Reports UI
Пропущенный между Epic 1 (миграция плана счетов ledger2) и Epic 2 (генераторы,
ожидающие ×1000 offset id) backend-слой. До этого коммита:
  - getLedger читал legacy laccounts (id 50/51/80/86);
  - BuhotchGenerator фильтровал по ledger2-id (51000/80000/86000) → фильтр
    пуст → реальный БУХ-баланс в ФНС уходил с нулями;
  - WalletsPage показывал chartOfAccounts вместо общекооперативных
    кошельков (1001/2001/3001/4001);
  - OperationsPage фильтровал клиентски, пропуская записи на
    невиданных ещё страницах пагинации.

### Backend (controller)

Domain `src/domain/ledger2/`:
- `interfaces/ledger2-account.interface.ts` — id (×1000), balance, debit/credit,
  account_type (0=active / 1=passive).
- `interfaces/ledger2-wallet.interface.ts` — id, name, available, blocked.
  Кошельки пайщиков живут в контракте soviet — сюда не попадают.
- `interfaces/ledger2-history.interface.ts` — Operation DTO + фильтр с
  action/accountId/date-range/username.
- `ports/ledger2-state.port.ts` — единая точка чтения ledger2.

Application `src/application/ledger2/`:
- DTO (Ledger2Account/Wallet/Operation/HistoryResponse).
- `resolvers/ledger2.resolver.ts` — 3 query (Accounts/Wallets/History) с
  @AuthRoles(chairman, member).
- `services/ledger2.service.ts` — маппинг domain → DTO, quantity/globalSequence
  в String (BigInt safety).
- Ledger2Module — registered в AppModule.

Infrastructure:
- `typeorm-ledger2-state.repository.ts`:
  - Accounts/Wallets: `SELECT DISTINCT ON (primary_key) value ... ORDER BY
    primary_key, block_num DESC` из blockchain_deltas WHERE code='ledger2'.
    Отдельной подписки не нужно — BlockchainConsumerService уже пишет deltas.
  - History: `blockchain_actions WHERE account='ledger2'` + серверные фильтры
    через параметризованный SQL (account_id → id/account_id/wallet_id JSON
    поля; action_code и username через `data ->>`).
  - Сортировка DESC по block_num+global_sequence.

report.resolver.loadLedger → ledger2Service.getAccounts. Теперь id совпадает
с BuhotchGenerator.ACCOUNT_GROUPS (×1000 offset), BUHOTCH даст реальные
балансы вместо нулей. ReportsExtensionModule теперь импортирует
Ledger2Module вместо LedgerModule.

### SDK
- Queries: `GetLedger2Accounts`, `GetLedger2Wallets`, `GetLedger2History`.
- Selectors с `MakeAllFieldsRequired`-валидацией.
- Queries.Ledger2 namespace, Selectors re-exports из `selectors/ledger2/`.
- schema.gql + zeus регенерированы (controller auto-gen при старте).

### UI (desktop)
- `src/entities/Ledger2/{api,types}.ts` — обёртки SDK.
- WalletsPage: источник → `ledger2Api.getWallets(coopname)`. Expand-row с
  LedgerHistoryTable удалён (оставлена кнопка «Смотреть операции» — ведёт
  в OperationsPage с прокинутым wallet_id). Отдельный Ledger2HistoryTable-
  виджет не писал — избыточно для Story 1.23.
- AccountsPage: источник → `ledger2Api.getAccounts`. Добавлена колонка
  «Тип» (Активный/Пассивный из account_type). Сальдо теперь реально берётся
  из поля balance (не computed-difference), дебет/кредит — debitBalance/
  creditBalance. Expand-история также удалён.
- OperationsPage: источник → `ledger2Api.getHistory`. Все фильтры ушли на
  сервер (action-names, username, date-range, accountId). Клиентская
  фильтрация удалена (она пропускала операции на ещё не догруженных
  страницах). Server-side пагинация через @request, seq-guard против race'а
  при быстрых кликах. route.query.account_id/wallet_id прокидываются в
  filter.accountId.

### Проверено

- Controller TS: `npx tsc --noEmit` — 0 ошибок в ledger2/reports scope.
- SDK TS: 0 ошибок.
- Desktop vue-tsc: 0 ошибок в reports/entities/Ledger2 scope (PaymentCard.vue
  имел 2 предыдущих ошибки, не связаны).
- Repo-layer SQL (через psql): возвращает корректные данные из
  `voskhod.blockchain_deltas` (51000/80000/86000 accounts, 1001/2001/3001
  wallets с актуальными balance/available).
- GraphQL endpoint: `POST /v1/graphql { getLedger2Accounts(coopname:"voskhod") }`
  отвечает 401 Unauthorized (guards работают), без auth — ожидаемо.

### Scope не входит

- Миграция legacy getLedger/getLedgerHistory (кошельки пайщиков, member-UI).
  Пока не трогаю — другие потребители ещё на legacy. Решим отдельно когда/
  нужно ли списывать legacy ledger полностью.
2026-04-23 13:30:36 +00:00
coopops c2c6e65592 [989-3][@ant] refactor(reports): code review Epic 3 — signerType persist + 18 silent UX-fix
DN1 (signerType persistence, настоящий баг отчётности):
  Раньше председатель выбирал «Представитель» в SettingsPage → сохранял
  signerRepDoc, но сам тип подписанта (chairman/representative) нигде не
  персистился и при generateReport бэкенд брал `org?.signerType ?? 'chairman'`.
  ФНС/СФР получали XML с ПрПодп=1 всегда, даже для представителя по
  доверенности. Формально подпись не соответствовала указанной персоне.

  Фикс:
  - report_requisites.signer_type (varchar(16), nullable) — миграция
    V2.0.1 идемпотентно добавляет колонку.
  - UpdateReportRequisitesInputDTO.signerType + валидация @IsIn.
  - ReportRequisitesViewDTO.signerType (String!, default 'chairman' из сервиса).
  - MergedRequisites.signerType — чистый choice, не RequisiteField.
  - report.resolver.resolveOrgFields берёт merged.signerType приоритетнее
    org.signerType (input-override оставлен для бэк-совместимости).
  - SDK: regenerated zeus + selector обновлён.
  - SettingsPage: save шлёт signerType; load восстанавливает из ответа.

Silent UX-fix (DocumentsPage):
  - B2: correctionsColumns → computed, иначе заголовки «На 31.12.YYYY»
    замирают на init-годе и вводят председателя в заблуждение при смене.
  - B5: debounce 400 + min/max 2000..2100 на year-input + UI-гвард перед
    loadArchive, чтобы keystroke «2026 → 2» не спамил бэк 400-ответами.
  - B6: onFilterChange сбрасывает page=1 перед loadArchive — иначе при
    смене типа отчёта со страницы 5 попадаешь в пустой offset.
  - B7/E1: triggerDownload — append anchor в DOM + setTimeout revokeObjectURL,
    чтобы Firefox/Safari не обрывали скачивание "Network error".
  - B9: openGenerate сбрасывает genPeriod=1 и genYear к дефолту, иначе
    значение monthly (period=8) уносится в quarterly и бэк отбивает Max(4).
  - B14: archiveTypeOptions строит label из reports (человекочитаемые
    имена), а не тех-коды BUHOTCH/NDFL6.
  - B15: corrections отправляется только для BUHOTCH — иначе бэк в
    resolveCorrections лишний раз лезет в balance_corrections.
  - E2: MIME для скачивания — application/xml без charset, чтобы работало
    и для cp1251 ФНС и для utf-8 СФР (XML declaration сам сообщит парсеру).
  - E3: guard `if (generating.value) return` — защита от двойного клика
    до того как loading prop обновится.
  - E5: lastArchiveRequestId-гвард — при быстрой смене страниц ответы
    могут прийти не по порядку, рендерим только последний.
  - E15: кнопка «Скачать XML» disabled если isValid=false + tooltip —
    председатель в спешке больше не скачает невалидный отчёт в ФНС.

Silent UX-fix (прочее):
  - E12: SettingsPage.save блокирует сохранение если signerType=representative
    и signerRepDoc пустой — иначе XML пойдёт с пустым <СвПред НаимДок=""/>.
  - B3/A4: AccountsPage «Сальдо» = available − blocked (а не копия available) —
    пайщик больше не видит две одинаковые цифры в двух соседних колонках.
  - B8/A11: OperationsPage scrollIntoView через data-seq-атрибут — ранее
    document.querySelector('[key="op_N"]') всегда возвращал null, т.к.
    Vue-шник :key не рендерится в DOM как HTML-атрибут.
  - B10: OperationsPage не позволяет wallet_id молча затереть уже
    выставленный account_id — явный if/else по query-params.
  - B11: SettingsPage.loadReadiness — console.error внутри silent catch,
    чтобы регрессии в селекторах не пропадали без следа.
  - B12: reportRequisitesViewSelector теперь запрашивает signerType
    (bundle вместе с DN1-regen).
  - B13: RequisiteField — эмодзи 🔗/✏️/⚠️ заменены на q-chip :icon.

Преднамеренно не делаю:
  DN2 (getReportPreview SDK+UI) — issue сам помечает follow-up.
  DN3 (WalletsPage ≠ AccountsPage) — Story 1.23 (_ledger2 read layer).
  DN4 (OperationsPage фильтр на backend) — зависит от Story 1.23.

BLOCKER: настоящая генерация BUHOTCH и отображение WalletsPage требуют
_ledger2 read layer в controller (Story 1.23). Сейчас getLedger читает
legacy ledger (id без ×1000), BuhotchGenerator ищет по ledger2-id
(×1000) — фильтр пуст, отчёт с нулями. Помечено отдельной задачей.
2026-04-23 13:30:35 +00:00
coopops aa56a8521c [989-2][@ant] refactor(reports): code review Chunk D (unit-тесты + fixtures) — закрыть настоящие баги генераторов, усилить регрессионный щит, убрать таутологические ассершны
Закрыты DN1..DN9 code review:

DN1 (uusn): добавлена валидация period ∈ 1..4 с осмысленной ошибкой —
раньше silent fallback `?? '21'` маскировал invalid input и продуцировал
отчёт с НомерМесКварт вне {01..04}.

DN2 (memory): validateAgainstXsd теперь вызывает xmlDoc.free() в finally —
синхронно с проддлинновым XsdValidatorService; без этого long-running
jest --watch копил native libxml2 handles до OOM.

DN3 (signer guard): assertRepresentativeSigner теперь вызывается и в
NDFL6/RSV/DUSN, а не только в BUHOTCH — регрессионный щит на ПрПодп=2+
СвПред+НаимДок закрыт для всех ФНС-форм что реально используют
representative-подписанта.

DN4 (diagnostics): beforeAll пробрасывает xsdLoadError наверх — если
XSD-схема сломается, Jest покажет один чёткий fail вместо 16+
невнятных «XSD не загружена».

DN6 (DRY): EFS1_XML_NS_MAP экспортируется из XsdValidatorService;
тест импортирует вместо копипасты — single source of truth, не
разойдётся при обновлении СФР-namespace.

DN7 (UUSN coverage + README): добило UUSN тесты (well-formed, key attrs,
fileName, quarter codes, throw на invalid period) — Story 2.11
теперь реально покрыта для всех 8 генераторов. README фикстур получил
таблицу «файл → форма» с КНД/ВерсФорм.

DN8 (tautology):
- NDFL6: тест «27 нулевыми атрибутами» теперь реально считает 27 через
  regex на открывающем теге вместо проверки 4 произвольных атрибутов.
- RSV: тест «<СвПред> НаимОрг» anchored к <СвПред ...> — раньше regex
  матчил НаимОрг в НПЮЛ тоже и проходил даже когда СвПред лишилось атрибута.
- BUHOTCH: тест балансов теперь реально сверяет числа (150000₽ → 150 тыс)
  + добавлен отдельный тест на corrections → СумПрдщ/СумПрдшв.

DN9: UUID regex якорит точный {8}-{4}-{4}-{4}-{12} формат;
ReportRegistryService import через ES вместо require().

Преднамеренно не фикшу: B7/B11/B12 (low-nits follow-up).
2026-04-23 13:30:35 +00:00
coopops 025da19ea5 [989-2][@ant] refactor(reports): code review Chunk C (preview + XSD validator) — закрыть дырку feature-flag, устойчивый путь к XSD, async-lock для chdir, единый источник правды для округления — чтобы prod-сборка видела схемы, параллельные валидации ЕФС-1 не смешивали cwd, а preview не расходился с XML по числам.
- DN1: generateReport теперь отклоняет HIDDEN_IN_MVP типы (PSV/UV_VZNOSY/UUSN)
  — раньше feature-flag работал только на UI (getAvailableReports +
  getReportPreview), mutation была открыта напрямую в GraphQL.
- DN2: resolveSchemasDir() — robust резолвинг пути через env override
  REPORTS_SCHEMAS_DIR + список кандидатов (src/, dist/../src/, cwd()).
  Работает и под ts-node (текущий prod), и после возможной компиляции в dist/.
- DN3: withEfs1Chdir() — async-мьютекс через очередь Promise'ов поверх
  process.chdir. Параллельные validate ЕФС-1 больше не могут перемешать cwd
  (libxml2 резолвит xs:import относительно cwd, это глобальное состояние).
- P1: DUSN preview убран ctx.year-1 → ctx.year (единый контракт с генератором
  после DN1 Chunk A).
- P2: validateByReportType с неизвестным XSD теперь isValid: false (раньше
  был isValid: true с error в массиве — downstream сохранял is_valid=true
  при наличии ошибки).
- P3: Preview «Сверка Актив=Пассив» с tolerance ±1 тыс. (ФНС 0710096 допускает)
  — раньше строгое `===` показывало ложное «Нет» при валидных отчётах.
- P4+P5: toThousands / ledger2DisplayIdToLedgerIds экспортируются из
  buhotch.generator; report-preview использует общий helper вместо дублированного
  round1000 — единый источник правды для арифметики.
- P6: CP1251_ENCODING_RE — устойчивый регекс, покрывает double/single quotes,
  case-insensitive, пробелы вокруг `=` (раньше не матчились варианты XSD).
- P7: libxmljs2 xmlDoc.free() в finally после validate — освобождение native
  памяти; без этого каждый вызов validate утекает, long-running backend OOM.
- validate/validateByReportType теперь async — чтобы mutex и future I/O
  работали корректно. Resolver await'ит результат.

Тесты: 61/61 report-generators зелёные.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:35 +00:00
coopops f0d3bc1b15 [989-2][@ant] refactor(reports): code review Chunk B (persist + requisites) — атомарность записи, настоящий UPSERT, защита от дырявого ledger, правильные DTO-валидации — чтобы половинчатые состояния в БД и «нулевые» отчёты из-за недоступного ledger не доходили до налоговой.
- P1 generateReport: сохранение отчёта + upsertMany корректировок в одной
  dataSource.transaction() (раньше два autocommit'а — при сбое корректировок
  отчёт уже был записан, расхождение со snapshot).
- P2 BalanceCorrectionTypeormRepository.upsertMany: одним bulk-INSERT ON CONFLICT
  вместо последовательного for-цикла (половинчатые записи при сбое невозможны).
- P3 ReportRequisitesTypeormRepository.upsert: настоящий .upsert() через
  ON CONFLICT вместо read-modify-write (убрана гонка между параллельными
  редактированиями одного coopname).
- P4 V2.0.0: CREATE EXTENSION IF NOT EXISTS "uuid-ossp" в начале up() —
  DEFAULT uuid_generate_v4() иначе падает на свежей БД.
- P5 findLatest: period=undefined теперь НЕ означает «только annual»; возвращает
  самый свежий отчёт за год независимо от периода (квартальные формы видят
  «last generated» в дашборде). period=null — явно годовые. period=число —
  точное совпадение.
- P7 loadLedger: убран try/catch-return-[] → ошибка ledger прокидывается,
  нельзя «успешно» сгенерировать нулевой отчёт из-за недоступного ledger.
- P8 list: period=null → IS NULL, число → точно, undefined → не фильтруем
  (симметрично findLatest).
- P9 generatedBy: убран fallback 'system'; при @AuthRoles(['chairman'])
  currentUser не может быть пустым, FALLBACK маскировал баг декоратора.
- DN1 getAvailableReports: добавлен @AuthRoles(['chairman']) +
  параллельный Promise.all вместо последовательного for-await.
- DN2 parseAmount: регекс `/(-?\d+(?:\.\d+)?)/` поддерживает отрицательные
  суммы; раньше знак терялся и убыток становился прибылью.
- P6 DTO валидация: @IsNotEmpty, @Length/@MaxLength, @Matches (ИНН 10/12,
  КПП 9, ОГРН 13/15, ОКТМО 8/11), @Min/@Max (year 2000..2100, period 1..54,
  correctionNumber 0..999, limit 1..100, offset ≥ 0) — невалидные входы
  теперь 400, а не SQL-ошибка 500.
- Throw NotFoundException/BadRequestException вместо plain Error (getReport,
  getReportPreview HIDDEN_IN_MVP, generateReport readiness) — GraphQL отдаёт
  структурированную ошибку.

Не трогали (по триажу):
- UNIQUE без report_type в balance_corrections — intentional (корректировки
  общие для всех форм coop+year+account).
- organization_snapshot SNILS plaintext — отдельный compliance-тикет.
- Дублирующие индексы TypeORM — косметика.

Тесты: 61/61 report-generators зелёные.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:35 +00:00
coopops 4fb2a847d5 [989-2][@ant] refactor(reports): code review Chunk A (генераторы ФНС/ФСС) — синхронизировать ИдФайл с именем файла, единый контракт input.year, почистить ledger2-маппинг и поправить СФР TZ — чтобы ФНС/СФР приёмка не отклоняла отчёт из-за несогласованного UUID и зарубежного часового пояса бэкенда.
- Крит 3: buhotch/dusn/ndfl6/rsv/uusn/uv-vznosy — generateFileName() кэшируется в generate(),
  передаётся в buildXml(input, idFile) одним параметром. Раньше было 2 вызова →
  2 разных UUID, filename на диске и ИдФайл в XML не совпадали → отказ ФНС-приёмки.
- Крит 6 / DN1: dusn.generator убран year-1; единый контракт input.year =
  «год за который отчитываемся» во всех ФНС-генераторах. UI по умолчанию
  подставляет currentYear-1; тест ДУСН обновлён (было year:2026→ОтчетГод:2025,
  стало year:2025→ОтчетГод:2025).
- Крит 9: ledger2DisplayIdToLedgerIds теперь игнорирует subaccount — в ledger2
  субсчета 86.x удалены (Epic 1 addendum), все корректировки пользователя
  с display-id «86.01»/«86.1» резолвятся в родительский счёт 86000.
  Раньше «86.01» → 8601000, и корректировка молча не применялась.
- Крит 10: fss4.sfrDateTime — hardcode Moscow TZ (+03:00). Раньше брался
  локальный TZ хоста → UTC-контейнер писал «+00:00» не соответствуя СФР.
- M2: uv-vznosy.generator — валидация input.period ∈ [1..12] с явной ошибкой
  вместо silent «НомерМесКварт=undefined»/квартал-overflow.
- M3: buhotch BalanceRow — переименовал поля prdш/prdsh (Cyrillic/Latin-mix)
  в prdPrev/prdPrePrev (Latin), чтобы избежать confusable-identifier багов.
- M5: buhotch correctionNumber валидация (целое 0..999) — раньше отрицательные/дробные
  значения молча писались в атрибут, ФНС XSD отклонял.

Не трогали (по решению review): РСВ/6-НДФЛ/FSS4 структуру (пустой <РасчетСВ/>,
ставка "13", Cyrillic namespace) — они соответствуют эталонам ВОСХОДа, которые
уже были приняты налоговой. ДУСН ПризНП=1 (кооператив не платит зарплату).

Тесты: 61/61 report-generators зелёные.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:35 +00:00
coopops 0148cd1e58 [989-1][@ant] refactor(boot-tests): code review Chunk 3 — ужесточить ассершны migrate-теста и почистить мёртвый код кошелька — чтобы silent-pass на warm-chain не прятал регрессии, повторный migrate действительно не менял state, а тест-хелперы падали на NaN-amount вместо криптичного asset-parse.
- P1 AC5: падать если accounts[99] не создан при свежем миграционном прогоне (было silent-pass на undefined) [ledger2-migrate.test.ts]
- P2 AC6: expect(acc).toBeDefined() перед чтением .balance у cash/share/entry (TypeError → понятный fail) [ledger2-migrate.test.ts]
- P3 AC7: snapshot meta + балансов ДО и ПОСЛЕ повторного migrate() — проверяем что migrated_coops/last_migrated_coop_index/debit_balance(51)/credit_balance(80) не изменились [ledger2-migrate.test.ts]
- P5 Заменить literals Number().toBe(0)/(1) на LedgerAccountType.ACTIVE/PASSIVE enum (экспортирован из walletUtils) — устойчивость к переименованию типов [ledger2-migrate.test.ts + walletUtils.ts]
- P6 depositToWallet(amount): Number.isFinite + amount > 0 guard — NaN/Infinity/отрицательные значения теперь дают понятную ошибку до сериализации в asset [depositToWallet.ts]
- P7 Dead-code cleanup в wallet.test.ts: убраны tester1/walletProgramStates1/addUser — никогда не использовались в ассертах; вместо этого добавлены expect().toBeDefined() на wallet/program/depositId/userWallet

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:35 +00:00
coopops 804a1b150c [989-1][@ant] refactor(ledger2+process-registry): code review Chunk 2 — K1/K2/K3/K4/K6 — чтобы process_hash реально работал как «нитка» всего процесса (cross-account scan), миграции не сливались в одну zero-hash кучу, counter'ы не делали full-scan, акт-2-результат показывал долю и займ рядом, а не вместо.
K1 migrate unique process_hash:
- migrate.cpp генерирует детерминированный hash = sha256("mig::"+coopname+"::"+action_code)
  → каждая opening-проводка различима в реестре, не сливается в zero-hash.

K2 cross-account Phase A scan:
- V2.1.0 миграция: idx_actions_ledger2_process_hash переименован в idx_actions_process_hash
  и сделан полным (без WHERE account='ledger2') — обслуживает и ledger2-only,
  и cross-account запросы.
- ProcessRegistryService.getProcess теперь собирает ВСЕ actions по (process_hash, coopname),
  не только ledger2. В view.actions попадают source-action (wallet::depcpl,
  registrator::regist, capital::*, marketplace::*, soviet::*) + inline-трио ledger2.
- countActionsByHash тоже cross-account — отражает полный счёт процесса.

K3 countDeltasByHash rewrite:
- Убран full-scan `LOWER(d.value::text) LIKE '%hash%'`.
- Замена: per-location точный запрос по PROCESS_HASH_LOCATOR (индексы idx_deltas_*).
- countDeltasByHash/countDocumentsByHash теперь принимают processType для локализации scope.
- listProcesses фильтрует строки с неизвестным action_code (вместо fallback'а на raw code).

K4 act2shr/act2ln separation:
- Убрана агрегация cap.act2shr/cap.act2ln → cap.act2res.
- Каждый action_code теперь собственный process_type: share-вклад и погашение
  займа в акте-2 показываются РЯДОМ (один process_hash), но как разные бух-операции.
- PROCESS_HASH_LOCATOR получил оба ключа; IProcessType union обновлён
  (cap.act2res → cap.act2shr | cap.act2ln).

K6 account id scale consistency:
- ChartOfAccountsEntity.INTANGIBLE_ASSETS=4 откат активации — эта entity читает
  legacy `ledger` (scale 51, 80, 86 без ×1000), РИД живёт в ledger2 (id=4000).
  Для ledger2 плана счетов нужна отдельная entity с offset ×1000 (TODO в коде).
- Reports-генераторы (buhotch, report-preview) уже используют ×1000 консистентно.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:35 +00:00
coopops da44b98dbf [989-1][@ant] refactor(ledger2): code review Chunk 1 — закрыть D1/D2/D3/D4 + защитные проверки — чтобы гарантировать парность walletop+debit+credit (sender-guard), убрать дублирующиеся нотификации кооперативу и закрыть потенциальные «тихие» потери legacy-остатков при миграции.
- D1: sender-guard в walletop/debit/credit — допустим только inline из apply (парность double-entry гарантирована, top-level вызов с ledger2@active запрещён)
- D2: TODO(payer) в walletop/debit/credit — payer=get_self() временно до общего перехода на coopname+eosio.code
- D3: read_legacy_balances аварит на неожиданном legacy id + проверяет символ валюты (silent-drop заменён на check(false))
- D4: повторный migrate() после полного прогона — тихий no-op без eosio::check (тест AC7 обновлён)
- apply: require_recipient после валидации coopname (не до)
- walletop: ISSUE требует wallet_from==0, BLOCK/UNBLOCK требуют wallet_to==0
- walletop/debit/credit: убран require_recipient (дублировал notification из apply)
- accounts2::is_empty() теперь включает поле balance
- actions.hpp: добавлен static_assert(wallets_exist_in_registry) — compile-time проверка что wallet_id из ACTION_REGISTRY существуют в LEDGER2_WALLET_REGISTRY
- migrate: guard против permanent-lock на пустой таблице cooperatives

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:35 +00:00
coopops f48ff28628 [989-1][@ant] refactor(ledger2): пересмотр плана счетов + RAM-чистка журналов + atomic 3-inline apply — закрыть Decision #1 code review (миграция через apply с двойной проводкой), убрать дублирование журнала из RAM (история уже в blockchain_actions+deltas), и подготовить контракт к РИД-корректировке Восхода 56.8M RUB.
Контракт ledger2:
  - План счетов сжат до 7 (04 НМА, 51 расч, 58 фин-вл, 67 займы, 80 паевой, 86 целевое, 99 транзит). Субсчета 86.x удалены.
  - Кошельки переименованы и пронумерованы ×1000 (1001 CASH_MAIN, 2001-2003 паевые, 3001-3003 целевые, 4001-4002 sinks, 4050/4052 займы); off-chain агрегаторы (1000/2000/3000) не создаются ончейн.
  - ACTION_REGISTRY перепривязан + добавлены mig.opncash/opnshr/opnent/opnrid; CONVERT_TO_AXN → Dr 80 / Cr 86.
  - Удалены таблицы journal+wjournal из RAM (история = action traces, парсер уже их захватывает).
  - apply() стал orchestrator-ом; рассылает 3 атомарных inline action: walletop / debit / credit, связанных общим process_hash.
  - В accounts2 добавлено поле balance (пересчитывается в debit/credit).
  - migrate(from_coop_index, limit) — курсорный режим через серию apply(OPENING_*) с RID-коррекцией для Восхода.
  - constexpr std::array + static_asserts (уникальность кодов, Dr≠Cr, wallet_from≠wallet_to, accounts_exist), memo cap, coopname validation.
  - soviet/converttoaxn: scope = coopname (а не _provider).

Backend контроллер:
  - ProcessRegistryService Phase A теперь сканирует blockchain_actions[ledger2] вместо deltas[wjournal/journal].
  - Добавлен ACTION_CODE_TO_PROCESS_TYPE для вывода process_type из action_code (ACTION_REGISTRY синхронизирован).
  - Миграция V2.1.0 убрала индексы wjournal/journal, добавила idx_actions_ledger2_process_hash + apply_action_code/username.
  - Cooptypes IProcessType +mig.opening/mig.rid; chart-of-accounts.entity +INTANGIBLE_ASSETS; reports-генераторы (buhotch, preview) убрали 86.x из targetFunds.

Тесты:
  - ledger2-migrate.test.ts переписан под новую схему: 8/8 проходит на live стенде.
  - fakeDocument в soviet/wallet тестах → IDocument2-схема (через shared/fakeDocument).
  - vitest fileParallelism: false — гарантия отсутствия гонок ончейн-state между файлами.
2026-04-23 13:30:35 +00:00
coopops e0d2d5266c [989-4][@ant] fix(process-registry): end-to-end работает на живом стенде — baseline через live blockchain+parser+controller
FIXES после live-прогона через pnpm run reboot + add-test-user:

1) parser/src/config.ts: добавлены ledger2+marketplace в subscribedContracts —
   без этого parser не пускал ledger2-дельты в Redis stream и controller не
   получал wjournal/journal, т.е. весь pipeline стоял.

2) controller/src/infrastructure/blockchain/blockchain-consumer.service.ts:
   processDeltaDelayed фильтровал по `delta.value?.coopname`, но ledger2
   (wjournal/journal/wallets/accounts) и большинство кооп-scope таблиц
   хранят coopname В SCOPE, а не в value.jsonb. Добавлен fallback на scope:
   `deltaCoop = delta.value?.coopname ?? delta.scope`.

3) domain/process-registry/services/process-registry.service.ts:
   - LEDGER2_CODE изменён с `_ledger2` на `ledger2` (имя on-chain аккаунта
     реальное, без подчёркивания — verified через cleos get abi ledger2).
   - phase A + listProcesses: coopname-скоупинг по `d.scope` (вместо
     несуществующего value->>'coopname' для ledger2 journals).
   - phase B (scanEntityDeltas): принимает оба варианта — `scope = $coop
     OR value->>'coopname' = $coop`, чтобы охватить и per-coop-scope
     таблицы, и singleton-scope контракты (registrator.regs).
   - LOWER() обе стороны при сравнении process_hash: ончейн хранит
     checksum256 uppercase, а нормализация API — lowercase.
   - listProcesses возвращает processHash в lowercase через LOWER() в
     SELECT (единообразно с getProcess).
   - countDeltasByHash/countDocumentsByHash: LOWER() + scope=coop.

4) migrations/V2.1.0: expression-индексы ledger2 journals теперь на
   (process_hash, scope) и (process_type, scope) — совпадают с фактическим
   where-условием сервиса.

5) cooptypes/common/names: `_ledger2.production/testnet = "ledger2"`
   (без подчёркивания, соответствует on-chain имени).

6) boot: добавлен CLI `pnpm run cli add-test-user <username>` для smoke-
   проверки Epic 4 на живом стенде после reboot. Также установлен
   `registration_hash: generateRandomSHA256()` в:
   - boot/init/infra.ts: adduser(ant) + adduser для 4 дополнительных
     членов совета (boot:extra mode);
   - boot/init/participant.ts: addUser+addUser2.

ПРОВЕРКА (live через curl + JWT подписанный JWT_SECRET из .env):

cleos get table ledger2 voskhod wjournal — 2 записи:
  id=0 reg.minshare, process_type=reg.regist, process_hash=<sha256>
  id=1 reg.entrfee,  process_type=reg.regist, process_hash=<sha256>
  (тот же hash — мульти-операционный процесс reg.regist)

query { process(hash:"28fe0b46...",coopname:"voskhod") }
→ process_type="reg.regist"
  delta_history: 4 (2 wjournal + 2 journal)
  actions: 3 (registrator::adduser + 2×ledger2::apply)
  documents: []

query { processes(filter:{coopname:"voskhod"}, pagination:{...}) }
→ totalCount=1, processHash lowercase, actionCount=3, deltaCount=4

Redis cache: ключ `process::voskhod::<hash>`, TTL=60s ✓
Auth: без JWT → 401 Unauthorized ✓

pnpm test — 67/67 passed (все unit-тесты по-прежнему зелёные).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:34 +00:00
coopops 0b8d1dfebd [989-4][@ant] feat(ledger2+process-registry): единый реестр процессов по process_hash — закрыть 11/12 stories Эпика 4, остался только smoke E2E на testnet
КОНТРАКТЫ (C++/CDT):
- actions.hpp: ledger2_ops::* переименованы с контрактным префиксом (reg./wall./cap./mkt./sov.),
  ActionRegistryEntry.process_type + static_assert unique(action_code); runtime-проверок нет —
  CPU-бюджет блокчейна не тратится на то, что гарантировано сборкой.
- process_types.hpp: новый namespace с 9 константами процессов (мульти-операционные cap.act2res,
  mkt.offereq, reg.regist явно разрешены).
- wjournal/journal: поля process_type/process_hash + secondary indexes byproctype/byprochash.
- apply(): document_hash → process_hash; emplace пишет process_type из registry в оба журнала.
- registrator::adduser: +checksum256 registration_hash параметр, inline sha256(username_str)
  удалён — все entity-хэши теперь приходят извне и годятся как process_hash.
- soviet::converttoaxn: +checksum256 process_hash параметр; отдельной ончейн-таблицы конверсий
  нет (одноактовый процесс), бэкенд передаёт statement.hash явно.
- Все 6 затронутых контрактов собираются (ledger2/registrator/soviet/wallet/marketplace/capital).

БЭКЕНД (NestJS):
- domain/process-registry/: ProcessRegistryService c двухфазным алгоритмом (anchor scan по
  _ledger2/wjournal+journal → fan-out по PROCESS_HASH_LOCATOR → документы через DocumentAggregator);
  Redis TTL 60s; fail-fast на неизвестный process_type; hard limit 200 с ошибкой (не обрезанием).
- listProcesses: DISTINCT ON (process_hash) по wjournal с пагинацией через PaginationInputDTO +
  createPaginationResult<ProcessSummary>.
- application/process-registry/: Resolver с Query.process + Query.processes под
  GqlJwtAuthGuard + AuthRoles(['chairman','member']).
- migrations/V2.1.0__process_registry_jsonb_indexes.ts: 11 partial-indexes на blockchain_deltas
  (ledger2 journals + все таблицы из PROCESS_HASH_LOCATOR) — без них getProcess делает seq scan.
- install/participant interactors: прокидывают sha256(username) как registration_hash; system.adapter
  прокидывает statement.hash как process_hash в converttoaxn.
- redis.module.ts: REDIS_PROVIDER в exports (нужен для ProcessRegistryService inject).

SDK:
- cooptypes: Ledger2Contract (IApply/IProcessType/IProcessView/IProcessSummary/IProcessesFilter/
  IProcessAction/IProcessDelta/IProcessDocument); IAdduser.registration_hash,
  IConverttoaxn.process_hash; _ledger2 в common/names.
- sdk/src/zeus: автогенерация controller schema.gql → ProcessView/ProcessSummary/ProcessesFilter
  + query.process/query.processes в namespaces Queries.
- Controller startup OK, SDK build OK (343kB).

ТЕСТЫ:
- tests/unit/process-registry/: 6 unit-кейсов ProcessRegistryService (одноактовый sov.axncnv,
  мульти-операционный cap.act2res с 2 entity-локациями, wall.deposit без документов, валидация
  hex-64 hash, fail-fast на unknown process_type, 404 без якорей).
- jest.config.js: moduleNameMapper для ~/ алиасов (иначе ts-jest не резолвит импорты).
- pnpm test — 67/67 passed (61 существующих + 6 новых).

ОСТАЛОСЬ (4.12):
- Smoke E2E на testnet — требует деплой контрактов, репарсинг с генезиса, ручной прогон
  5 сценариев (регистрация/депозит/долг/акт2/конвертация) + сохранение фактических результатов.
  Чек-лист готов в _bmad-output/implementation-artifacts/4-12-smoke-results.md.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:34 +00:00
coopops 1e6eeb5233 [989-3][@ant] feat(reports): рабочий стол reports — 5 страниц (Operations/Wallets/Accounts/Documents/Settings) + регистрация расширения и SDK-типы
Закрыть Epic 3 целиком (Stories 3.1–3.8), чтобы отчёты ФНС/ФСС были доступны как полноценный workspace вместо голой страницы генерации, с деплинком между операциями/кошельками/счетами и с валидацией реквизитов до нажатия «Сгенерировать».

- extensions.registry.ts: раскомментировать reports-модуль, чтобы бэк отдавал его в AppRegistry.
- desktop/extensions/reports/install.ts: 5 маршрутов (operations/wallets/accounts/documents/settings), роль chairman на всех.
- OperationsPage: virtual-scroll, клиентские фильтры (период/action/user/memo), expand с проводкой+движением+кнопками «К счёту»/«К кошельку», scrollIntoView по operation_id из query.
- WalletsPage: таблица без writeoff, expand с LedgerHistoryTable по account_id=wallet_id, кнопка перехода в OperationsPage.
- AccountsPage: моноширинный displayId (дробная нотация 86.01), expand c журналом проводок, кнопка «Журнал».
- DocumentsPage: архив getReportHistory + isValid-чипы + «Скачать» через getReport(id), feature-flag 5 форм (BUHOTCH/NDFL6/RSV/DUSN/FSS4), индикаторы readiness, форма корректировок прошлых периодов для BUHOTCH (передаётся как corrections[] в generateReport).
- SettingsPage + RequisiteField: 4 раздела (organization ro/классификаторы/СФР/подписант), бейдж источника (блокчейн/manual/empty), индикаторы готовности по 5 формам через checkReportReadiness, scrollIntoView к полю по query.focus.
- entities/Report: reportApi обёртка над SDK (getAvailableReports, getReport, getReportHistory, getReportRequisites, checkReportReadiness, generateReport, updateReportRequisites).
- SDK: selectors/queries/mutations reports/, namespaces Queries.Reports + Mutations.Reports. Регенерация Zeus-типов через generate-client в контейнере coopback (libxmljs2 пересобран под Node 22).
- schema.gql: обновлена штатным autoSchemaFile при старте controller в coopback.
- удалён старый ReportsPage/ — DocumentsPage единственная точка входа.

typecheck desktop и SDK — чистые; controller имеет 3 пре-existing ошибки в appstore/extension и gateway, не связанные с Epic 3.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:34 +00:00
coopops 6dc161e69f [989-2][@ant] feat(reports): подключить XSD-валидацию ЕФС-1 (СФР) — закрыть последний AC Story 2.7, чтобы 4-ФСС проходил проверку по официальной схеме СФР ещё до попытки сдачи и не ловил отказ на приёмке из-за пустой ДатаЗаполнения или сдвига namespace
Добыта XSD EFS-1_2024-01-01.xsd с сайта СФР + 7 зависимостей, положена в
schemas/efs1/ с двумя патчами: кириллические URI в namespace на ASCII
(libxml2 отвергает http://пф.рф/) и сдвиг дат 2024-01-01 → 2026-01-01 под
формат КОНТУР-ЭКСТЕРН; XsdValidatorService определяет кодировку XSD по
заголовку и делает chdir для резолвинга xs:import; генератор заполняет
<ДатаЗаполнения> по xs:date. Добавлен XSD-тест, 61/61 зелёный.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:33 +00:00
coopops 966d342be6 [989-2][@ant] test: заменить реальные отчёты ВОСХОДа на санитизированные фикстуры ПК "Ромашка" — чтобы unit-тесты генераторов работали в публичном CI и не утаскивали живые ИНН/КПП/ОГРН/ФИО в гит
- components/controller/tests/fixtures/reports-references/ — 5 эталонных XML (NO_BOUPR/NO_NDFL6.2/NO_RASCHSV/NO_USN/EFS1) с вымышленными реквизитами (ИНН 7701234567, ПК "Ромашка", Петров П.П.) + README
- тест переключён на новый REFERENCES_DIR; baseInput также теперь ромашка
- добавлен кейс «EFS1: та же структура ОСС» — 58/58 зелёных
- story 2.7 (ЕФС-1) переведена в done: XSD СФР нет в публичном доступе, структурная сверка с фикстурой закрывает регрессии
- .gitignore расширен шаблонами для реальных XML с ИНН 9728130611 / рег.СФР 1118018397, чтобы подобные образцы не утекали в гит из любых подпапок reports-standarts/

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:33 +00:00
coopops 7b91168836 [989-2][@ant] test: добавить unit-тесты всех 8 генераторов отчётности ФНС/ФСС в controller (story 2.11) — чтобы регрессии в XML-выхлопе ловились до сдачи отчёта, а не в проде
- новые 57 jest-кейсов в tests/unit/reports/ покрывают BUHOTCH, NDFL6, RSV, PSV, DUSN, ЕФС-1, UV_VZNOSY, UUSN
- структурная сверка с эталонами ВОСХОДа (reports-standarts/) + XSD-валидация по 6 доступным схемам через libxmljs2
- pnpm run test на controller переведён с echo-заглушки на jest (интеграция сохранена в test:integration)
- попутно пофикшены баги в uv-vznosy/uusn: атрибуты Период/НомерМесКварт не проходили XSD (был "21/01" вместо одного из {21,31,33,34}; номер без zero-padding)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-23 13:30:33 +00:00
coopops 9a6624f532 [989-2][@ant] feat(reports): снять блокер Story 2.3 — положить XSD 5.04 КНД 0710096 (ЕД-7-1/1041) и починить генератор BUHOTCH под неё, чтобы валидация баланса НКО проходила без ошибок и не пришлось копипастить эталонный баг КОНТУРа с пустым НаимФайлПЗ 2026-04-23 13:30:33 +00:00
coopops 061ef30fce [989-2][@ant] feat(reports): добавить справочник реквизитов кооператива и readiness-проверку перед генерацией — epic-2 story 2.10, чтобы система сразу блокировала сдачу форм с недостающими данными (ОКВЭД/ОКТМО/регномер СФР) и автозаполняла ИНН/КПП/ОГРН из блокчейна вместо ручного копипаста 2026-04-23 13:30:33 +00:00
coopops 12d5a46d7e [989-2][@ant] feat(reports): добавить getReportPreview + feature-flag скрытых форм и lastGeneratedAt в availableReports — epic-2 story 2.8, чтобы председатель видел рассчитанные строки баланса перед генерацией XML и понимал, когда в последний раз сдавал форму 2026-04-23 13:30:33 +00:00
coopops f2309f1c4c [989-2][@ant] feat(reports): переписать нулевые генераторы 6-НДФЛ/РСВ/ДУСН/ЕФС-1 под эталоны ВОСХОДа — epic-2 stories 2.4-2.7, чтобы сгенерированные XML реально проходили XSD ФНС и не отклонялись при электронной сдаче 2026-04-23 13:30:33 +00:00
coopops dc3e5753d6 [989-2][@ant] feat(reports): добавить персист отчётов, историю и авто-предзаполнение корректировок — epic-2 story 2.9, чтобы председатель видел архив сгенерированных XML и не перевводил правки балансов при повторной генерации 2026-04-23 13:30:33 +00:00
coopops 08dd3a2a25 [989-2][@ant] feat(reports): переписать BUHOTCH-генератор под эталон ВОСХОДа — потребкооператив сдаёт форму НКО (КНД 0710096, ВерсФорм 5.04), а не коммерческую 0710099/5.09, иначе отчёт не примут 2026-04-23 13:30:33 +00:00
coopops 4a76b6aac0 [989-2][@ant] feat(reports): добавить таблицы истории отчётов и XSD-валидатор (epic-2 stories 2.1, 2.2)
- Story 2.1: entity generated_reports + balance_corrections, TypeORM-репозитории, идемпотентная Flyway-миграция V2.0.0.
  Entity авто-дискаверятся через глоб src/extensions/**/entities/*entity.{ts,js}. Без UNIQUE на
  (coopname,report_type,period) — пересоздание допустимо; UNIQUE на (coopname,year,account_display_id)
  для upsert корректировок.
- Story 2.2: XsdValidatorService поверх libxmljs2 с кэшированием всех 6 XSD из schemas/,
  перекодировкой cp1251→utf8 и мержем ошибок в GeneratedReportDTO.errors. Смоук: эталонный BUHOTCH
  парсится, .validate() корректно отдаёт как позитив, так и детальные семантические ошибки.

Находка для Story 2.3: установленная XSD — v5.09 КНД 0710099 (коммерческая), эталон ВОСХОДа — v5.04
КНД 0710096 (форма НКО). Либо добыть XSD 5.04, либо переключить генератор на 5.09.
2026-04-23 13:30:33 +00:00
coopops 4b3e24fd86 [989-1][@ant] feat: мигрировать legacy-ledger параллельно в оба контура ledger2 (wallets + accounts) — иначе после переключения мы теряем состояние бухбаланса 51/80/861 и другие счета на миллионы RUB, а новые apply-вызовы стартуют поверх пустой бухгалтерии
— migrate.cpp: для каждой ненулевой laccount сумма total=available+blocked кладётся в ledger2::accounts[legacy_id*1000] в правильное плечо оборотов (ACTIVE/A-P → debit_balance, PASSIVE → credit_balance); при наличии целевого фонда параллельно заполняется wallets (SHARE_FUND=2, ENTRANCE_FEES=3, LONG_TERM_LOANS=6)
— маппинг legacy→ledger2 задокументирован в PRD §4.1.5 таблицей (FR-L-13) + issue 989-1: 51→51000(A,Dr), 80→80000(P,Cr)+wallet2, 861→861000(P,Cr)+wallet3, 67→67000(P,Cr)+wallet6
— зафиксирована follow-up миграция (Story 1.11 backlog): вычленение минимальных паевых взносов из wallets[SHARE_FUND=2] в wallets[MIN_SHARE_FUND=1] по количеству пайщиков × размер обязательного пая; accounts не трогается (проводка Dr51/Cr80 одна и та же)
— интеграционный тест расширен с 8 до 9 AC: AC5/AC6 теперь проверяют что BANK_ACCOUNT и MEMBER_DEBT мигрируют в accounts (Dr), но не создают кошельков; AC7 отдельно проверяет credit_balance для 80000/861000/67000
— legacy одноконтурный, поэтому Σ Dr ≠ Σ Cr после миграции — это ожидаемо и задокументировано в миграции
2026-04-23 13:30:33 +00:00
coopops 83135df044 [989-1][@ant] refactor: завершить epic-1 ledger2 — починить boot-тесты, исправить маппинг legacy→ledger2 id в migrate и убрать тавтологичный validateJournalInvariant как оверинжиниринг
— починка интеграционных тестов capital.test.ts после переключения wallet/capital на Ledger2::apply: helper-ы walletUtils.ts теперь читают ledger2::accounts[80000], available синтезируется из (credit-debit) для PASSIVE-счетов; circulationAccountId=80_000
— migrate.cpp получил маппер legacy_to_wallet_id (80→2 SHARE_FUND, 861→3 ENTRANCE_FEES, 67→6 LONG_TERM_LOANS); writeoff + нулевые + не-фондовые счета (51, 751) пропускаются; идемпотентность через meta
— новый integration-test ledger2-migrate.test.ts (8 AC: seed legacy → migrate → маппинг → идемпотентность)
— удалён application/ledger2/ модуль: validateJournalInvariant был тавтологией (totalDebit += amount; totalCredit += amount — разница всегда 0); инвариант Σ Dr = Σ Cr гарантирован контрактом, backend-проверка не добавляет гарантий
2026-04-23 13:30:33 +00:00
coopops e8859f943e fix boot 2026-04-23 13:30:33 +00:00
coopops 768ce8ec82 fix boot 2026-04-23 13:30:33 +00:00
coopops 6dd8f7724a make docker containers runnable 2026-04-23 13:30:33 +00:00
Alex Ant 448b6000a3 [989-1][@ant] feat: внедрить ledger2 с apply и переключить контракты-инициаторы с legacy ledger — нужна двойная запись и единый API именованных операций для миграции остатков и регуляторной отчётности
Made-with: Cursor
2026-04-23 13:30:32 +00:00
Alex Ant 13881a9c0b Merge pull request #360 from coopenomics/graph-standarts
feat(standards-site): реестр кооперативных стандартов v1 — graph-standarts → dev
2026-04-23 18:25:20 +05:00
coopops f80a6fdf47 [350-1][@ant] feat: вынести реестры ledger2 в cooptypes, slim-YAML §6 и деплой standards-site на /standards — один TS-источник правды для имён счетов/кошельков (standards-site + desktop/shared/lib/ledger2 станет re-export после мёржа в reports), spec манифеста приведена к тому что реально рендерит фронт (без ролей-enum, без scenario, без Doxygen-id), FocusBar показывает Проводки/Переводы отдельными карточками с tooltip-подсказками из @coopenomics/cooptypes, клик по × и ● даёт описание из YAML, автопан при навигации ←/→, мобильная заглушка <900px, scrollBehavior при переходе на related; публикация через mono publish-docs с base=/standards/ и ссылкой в mkdocs nav, чтобы председатели сразу попадали на визуальный паспорт процесса с docs.coopenomics.world 2026-04-23 10:45:02 +00:00
coopops 948388d7e8 [350-1][@ant] feat: собрать прототип реестра кооп-стандартов v1 (standards-site) — vite/vue3 сайт читает YAML-манифест рядом со смарт-контрактом и рендерит BPMN-подобный граф процесса (∅ старт → прямоугольники-статусы → action-таблетки с иконками-индикаторами документ/кошелёк/проводка → ● финиш), фокус через ?s/?a/?d/?o, стартовая карточка показывает purpose из YAML, добавлены два пилота reg.regist и wall.deposit, чтобы председатели получили читаемый паспорт процесса из одного источника правды без параллельной markdown-документации, которая расходится с кодом 2026-04-23 07:22:47 +00:00
coopops b35ef8ccba [549-25][@ant] config: пометить @coopenomics/parser приватным — пакет переехал в coopenomics/parser как 1.0.x и публикуется оттуда, старый 2026.x поток в mono больше не нужен; private true исключает его из lerna publish не ломая локальную сборку в workspace, другие пакеты (sdk, cooptypes, factory, provider-client) продолжают пушиться без изменений 2026-04-22 16:05:59 +00:00
coopops d32af78fed [549-24][@ant] config: убрать сборку и push dicoop/cooparser из build-containers.yaml — парсер переехал в отдельный репо coopenomics/parser и теперь публикуется как dicoop/parser из его release.yml, двойной источник одного образа (cooparser vs parser) создавал бы коллизию тегов и риск несогласованности версий; остальные контейнеры (mono-base, desktop, coopback, notificator, notifications) продолжают собираться как раньше 2026-04-22 16:04:43 +00:00
coopops 0c5e04a484 [0C1-6][@ant] fix(generate-schema): принимать резолверы с @Resolver() без параметра — устраняет регрессию генерации schema.gql, где терялось 40 из 48 резолверов и десятки input-типов (LoginInput, ResetKeyInput, GenerateDocumentInput, весь блок AnnualGeneralMeeting*Input)
Корневая причина: discoverResolverClasses отфильтровывал по `Reflect.getMetadata(RESOLVER_TYPE_METADATA, exp) === undefined`. Декоратор @Resolver() без аргумента выставляет метаданные через Nest-овский SetMetadata(RESOLVER_TYPE_METADATA, undefined) — defineMetadata реально выполнен, но getMetadata возвращает undefined, неотличимо от «не устанавливалось». В результате ровно те резолверы, что имеют @Resolver() без параметра, проваливались через фильтр (AuthResolver, MeetResolver, DocumentResolver, GenerationResolver, и т.п. — почти весь capital-extension и половина application/).

Фикс: использовать Reflect.hasMetadata, который корректно различает defined-as-undefined от undefined-by-absence. Теперь подхватываются все 48 резолверов (было 8).

Регенерированы schema.gql, zeus/index.ts, zeus/const.ts в обоих копиях (controller-local и sdk). SDK typecheck чист; desktop vue-tsc чист (единственная ошибка в PaymentCard — pre-existing, не из этого фикса).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-22 08:57:33 +00:00
coopops 124f0c4440 [562-14][@ant] fix: считать fact только по задачам в статусах DONE и ON_REVIEW — для активных задач estimate-билеты ещё не «факт», а предварительное распределение плана, его смешивать с отработанным временем нельзя
В withFactBatch/withFact добавлен предфильтр FACTUAL_STATUSES={DONE, ON_REVIEW}. Задачи в TODO/IN_PROGRESS/BACKLOG получают fact=0 в DTO, независимо от того что лежит в TimeEntry — прогресс-бар отобразит их как «не начато».

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-22 08:42:31 +00:00
coopops 86ad4aa819 Merge remote-tracking branch 'origin/dev' into dev 2026-04-22 08:37:03 +00:00
coopops 154a9f405b chore(env): добавить .env.example как шаблон per-instance конфига
Компонент к 8d037a9dbb — без .env compose поднимется с дефолтами
(базовый инстанс на портах 8888/27017/...). Для второго и далее
инстансов скопировать .env.example в .env и применить offset
+10/+20/+30 к host-портам.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-22 08:36:41 +00:00
coopops 0753db3d82 Merge remote-tracking branch 'origin/dev' into dev 2026-04-22 08:33:46 +00:00
coopops 8d037a9dbb feat(boot): параметризация инстанса через .env для параллельного запуска
Все mono-ai-N теперь могут работать одновременно на изолированной
инфраструктуре. Имена контейнеров автогенерируются compose-проектом
(префикс из .env), хост-порты и URL берутся из .env.

- docker-compose.yaml: убраны статические container_name, host-порты
  через ${VAR:-default} для обратной совместимости
- boot scripts (reboot/clean_reboot/extra_reboot/clear): source корневого
  .env и docker exec → docker compose exec -T (через service name)
- networks.sh, preactivate.sh: cleos/curl используют ${CHAIN_URL:-...}
- boot health.ts, configs/index.ts, configs/networks.ts: читают
  process.env.CHAIN_URL вместо hardcoded localhost:8888
- configs/contracts.ts: добавлен ledger2
- init/infra.ts: addUser получил недостающий registration_hash

В каждой папке mono-ai-N нужен локальный .env (в .gitignore) с
INSTANCE_INDEX, COMPOSE_PROJECT_NAME, host-портами и
CHAIN_URL/API_URL/MONGODB_URL. Без .env compose поднимется на дефолтных
портах (как у mono-ai-1).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-22 08:24:30 +00:00
coopops 671526e3ea [562-14][@ant] feat: показывать фактически накопленное время (fact) в карточке задачи и раскрывающуюся историю worklog — пользователь впервые видит прогресс работы против плана прямо в UI, без догадок
PR-1 по задаче 562-14 «Разделить учёт плана/факта времени»: read-only слой fact без изменений схемы БД и без мутаций.

Бэк (controller):
- time-entry.repository.ts — интерфейс getFactByIssues(hashes[]) → Map<hash, IssueFactAggregate> + тип aggregate'а
- time-entry.typeorm-repository.ts — одним SQL (SUM(hours) + SUM CASE committed/uncommitted, GROUP BY issue_hash, contributor_hash); N+1 исключён
- issue.dto.ts — @Field fact / fact_committed / fact_uncommitted / fact_by_contributor + CapitalIssueContributorFact
- generation.service.ts — generic withFact/withFactBatch (по паттерну withLinkedGitCommits); обогащаем getIssues (батч), getIssueById, getIssueByHash, createIssue, updateIssue, moveIssueToComponent

SDK:
- issueSelector.ts — fact-поля в селекторе (MakeAllFieldsRequired проходит)
- zeus/index.ts + zeus/const.ts — правки руками во все 4 блока (Value/Resolver/Model/GraphQL) и const-reflection; автогенерация через generate-schema уронила бы schema.gql (отдельный тикет)

Фронт (desktop):
- Estimation.vue — при fact>0 рендерит мини-прогресс-бар fact/estimate: teal в плане, orange перебор, grey без плана; tooltip с расшифровкой
- IssuesListWidget.vue — :fact='row.fact' передан в Estimation (full + compact)
- IssueControls.vue — строка «Факт» в сайдбаре с тем же прогрессом рядом с UpdateEstimate
- IssuePage.vue — q-expansion-item «История рабочего времени» с подписью «X ч из Y ч», разворачивает существующий TimeEntriesWidget (мобильный + десктопный layout)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-22 08:02:56 +00:00
Alex Ant fe6c9f3e53 chore(release): publish 2026-04-22 11:30:46 +05:00
Alex Ant 921d0a5163 chore(release): publish 2026-04-22 11:00:58 +05:00
Alex Ant 65b290827f Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-04-22 11:00:18 +05:00
coopops ff44889c10 [562-30][@ant] fix: пересчитывать estimate-билеты при смене creators и чистить их на удалении задачи, плюс ленивый recalc в createCommit — чтобы у участника не терялось доступное для capital-коммита время при обычной работе с задачами
- generation.service.ts:updateIssue — applyExplicitEstimateToTimeEntries вызывается при изменении множества creators, а не только estimate (сравнение через creatorsSetEquals)
- generation.service.ts:deleteIssueByHash — перед удалением issue чистим uncommitted TimeEntry, иначе остаются сиротами и искажают pending_hours
- time-tracking.interactor.ts — добавлены cleanupIssueTimeEntries и идемпотентный recalcDoneEstimatesForContributorProject (учитывает уже закоммиченные часы, committed записи не трогает)
- time-tracking.service.ts — проксирующий метод для recalc
- generation.interactor.ts:createCommit — перед getAvailableCommitHours дёргаем recalc: лечит расхождения, накопившиеся до фикса, без миграции БД

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-22 05:56:30 +00:00
coopops 9140a8ec5f docs: переместить macros-guide.md в корень components/docs
Файл — руководство для разработчиков документации по макросам
mkdocs (get_sdk_doc, get_typedoc_*, get_graphql_doc), не для рендеринга.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-22 04:42:27 +00:00
Alex Ant 8ff7fe12dd chore(release): publish 2026-04-20 00:10:40 +05:00
Alex Ant 739c5fdbdb chore(release): publish 2026-04-20 00:09:52 +05:00
Alex Ant fb1e4291fe generation edit requirements access fix 2026-04-20 00:09:13 +05:00
Alex Ant 7cd8418ad1 chore(release): publish 2026-04-19 23:50:54 +05:00
Alex Ant 9f3fad294a fix setMasterButton and add reposts standarts 2026-04-19 23:50:18 +05:00
Alex Ant de2ef85c68 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-04-19 23:49:15 +05:00
coopops d004718761 [162-7][@ant] feat: добавить blago del issue/req и orphan prune в pull — согласовать локальное состояние индекса с сервером и дать возможность реально удалять артефакты из CLI
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-19 17:12:16 +00:00
Alex Ant 6c977daa7d commit skill fix 2026-04-17 17:46:30 +05:00
Alex Ant a585e78fd9 ledger2 start 2026-04-17 01:55:08 +05:00
Alex Ant 9f8228c5b0 chore(release): publish 2026-04-16 00:07:24 +05:00
Alex Ant fdc4cdc3c1 chore(release): publish 2026-04-16 00:06:22 +05:00
Alex Ant b898a31b24 whisper fix 2026-04-16 00:05:42 +05:00
Alex Ant 9d6273182a chore(release): publish 2026-04-14 21:22:31 +05:00
Alex Ant 2474c24533 chore(release): publish 2026-04-14 21:21:27 +05:00
Alex Ant dc08108090 [562-29][@ant] fix: разрешить capitalEditProject пайщику и совету с проверкой can_edit_project — устраняем 401 guard при сохранении карточки проекта соавтором и выравниваем права AUTHOR в матрице доступа Capital
Made-with: Cursor
2026-04-14 21:19:35 +05:00
Alex Ant cff531fb28 chore(release): publish 2026-04-14 16:11:37 +05:00
Alex Ant 0a31890da9 chore(release): publish 2026-04-14 13:17:46 +05:00
Alex Ant eb0e19dd9c переход со страницы задачи на компонент осуществляется в раздел задач 2026-04-14 12:54:07 +05:00
Alex Ant f3a63a05d8 [562-28][@ant] fix: восстановить агрегацию артефактов по компонентам и оформить бейджи на списке проекта — чтобы пользователь видел полную картину по релизу и не терял контекст при открытии карточки артефакта с компонента
Made-with: Cursor
2026-04-14 12:45:18 +05:00
Alex Ant 944f4e1e75 [562-27][@ant] feat: взнос часов без Git и приватный отзыв в data коммита — чтобы участник мог фиксировать вклад без Git и не выносить текст отзыва в публичное description блокчейна для мастера и отчёта о результатах
Made-with: Cursor
2026-04-14 12:24:48 +05:00
Alex Ant c893ea1e41 [562-26][@ant] refactor: заменить пользовательские подписи «требования» на «артефакты» в расширении Capital desktop — единая нейтральная терминология для описаний, диаграмм и прочих материалов в интерфейсе Благороста
Made-with: Cursor
2026-04-14 10:51:52 +05:00
Alex Ant d397e00db0 chatcoop v5 migration for audio re-translation bug fix 2026-04-14 10:37:54 +05:00
Alex Ant 0c863c3176 chore(release): publish 2026-04-13 23:13:47 +05:00
Alex Ant 7dadb4cb88 fix: капитализация -> благорост 2026-04-13 23:12:32 +05:00
Alex Ant 0c57fe4f61 chore(release): publish 2026-04-13 22:25:45 +05:00
Alex Ant a1b46c9f4b chore(release): publish 2026-04-13 22:24:43 +05:00
Alex Ant b5ade47c47 [162-5][@ant] fix: процесс ре-синхронизации сервера 2026-04-13 22:23:14 +05:00
Alex Ant 6a26660be5 [C28-6][@ant] fix: переупорядочить нижний блок левого drawer — шеврон разворота остаётся у нижнего края под пальцем и снижает риск случайного выхода двойным тапом
Made-with: Cursor
2026-04-13 22:19:05 +05:00
Alex Ant 50c6281eec [562-26][@ant] fix: пагинация списков проектов и задач Capital desktop — передача options и устранение гонки виртуального скролла чтобы не дублировались строки при догрузке с бэкенда
Made-with: Cursor
2026-04-13 22:13:19 +05:00
Alex Ant 6a45039f93 chore(release): publish 2026-04-13 20:49:19 +05:00
Alex Ant 572465654f chore(release): publish 2026-04-13 20:47:18 +05:00
Alex Ant 02306f7f71 feat: фиксация заявления на инвестицию в программу в реестре документов 2026-04-13 20:45:22 +05:00
Alex Ant da00275572 [562-8][@ant] feat: перенос задач между компонентами одного проекта — мастерам не нужно дублировать задачи при смене компонента, сохраняются issue_hash и id, переносится время и связи Git до фиксации в CAPITAL
Made-with: Cursor
2026-04-13 20:43:50 +05:00
Alex Ant cea27e9dac [562-2][@ant] fix: фильтровать выдачу проектов Capital по полю present в репозитории и интеракторе — чтобы удалённые из блокчейна проекты и компоненты не показывались в списке и по прямой ссылке рабочего стола Благороста
Made-with: Cursor
2026-04-13 17:01:10 +05:00
Alex Ant 0d4c191bca chore(release): publish 2026-04-13 15:50:00 +05:00
Alex Ant 8382e8b464 chore(release): publish 2026-04-13 15:49:14 +05:00
Alex Ant fba4bb6786 [562-3][@ant] fix: Matrix-анонсы компонентов без закрепа и без лавины дублей — чтобы участники Оп!Кооп видели один понятный пост со ссылкой закрепы остались только у документов а Synapse реже отвечал M_LIMIT_EXCEEDED из-за повторной публикации и всплеска запросов
Made-with: Cursor
2026-04-13 15:47:06 +05:00
Alex Ant 9deee2e552 capital: migration complete 2026-04-13 14:21:37 +05:00
Alex Ant 798ad26ad7 blago commit commad improve 2026-04-13 14:20:04 +05:00
Alex Ant 3850945b67 chore(release): publish 2026-04-13 14:07:15 +05:00
Alex Ant 71e9303cdd chore(release): publish 2026-04-13 13:49:28 +05:00
Alex Ant 87d76b6b5e cleos fix 2026-04-13 13:48:33 +05:00
Alex Ant c0025d3665 [562-13] Интервал regshare в минутах; дефолт 1440; старт планировщика в initialize
[@ant]

Made-with: Cursor
2026-04-13 13:47:13 +05:00
Alex Ant 0a4d8e7fee chore(release): publish 2026-04-13 12:58:39 +05:00
Alex Ant 1b63a1430e [562-25] Capital: migrate contributed_as_investor для voskhod; импорт с суммой в поле инвестора
[@ant]

Made-with: Cursor
2026-04-13 12:57:11 +05:00
Alex Ant da8c443625 [562-13] regshare: кооператив, без inline в apprvappndx; планировщик долей Capital
[@ant]

Made-with: Cursor
2026-04-13 12:27:59 +05:00
Alex Ant 35936801c8 chore(release): publish 2026-04-13 11:11:11 +05:00
Alex Ant a8d12df993 chore(release): publish 2026-04-13 11:07:44 +05:00
Alex Ant b5ccffc4cf [562-15] Конфигурация git синхронизатора по дефолту не запускает синхронизацию
[@ant]
2026-04-13 11:05:06 +05:00
Alex Ant 8d8f238db5 [562-24] EntityIdBadge: иконка типа в бейдже, копирование [id][@логин] по клику в Capital
[@ant]

Made-with: Cursor
2026-04-13 10:58:32 +05:00
Alex Ant 0bddf3f21e chore(release): publish 2026-04-12 22:26:15 +05:00
Alex Ant 068f13523e [562-15] RID из суммы маркированных git-коммитов: синк GitHub, БД, Capital UI и SDK
[@ant]

Made-with: Cursor
2026-04-12 22:23:47 +05:00
Alex Ant c44c1adf18 fix: blago-cli merge & zeus client generation 2026-04-12 12:50:54 +05:00
Alex Ant 05309cd08f [562-23] createpinv: учёт contributed_as_investor у contributor
[@ant]

Made-with: Cursor
2026-04-12 10:40:18 +05:00
Alex Ant 77e62a8bbc [562-22] Capital: createinvest/createpinv через available; вырез sync program invest; рефакторинг нейминга
[@ant]

Made-with: Cursor
2026-04-11 22:25:19 +05:00
Alex Ant 86799c0c41 [562-1] Программная инвестиция createpinv: API, заявление 1030, desktop
[@ant]

Made-with: Cursor
2026-04-11 20:57:51 +05:00
Alex Ant 25e92297f9 generate schema script 2026-04-11 12:25:13 +05:00
Alex Ant da5b5a73f6 blago-cli ignore list fix & install skills only with options 2026-04-11 11:52:35 +05:00
Alex Ant 371735c6cc fix hint on estimate 2026-04-11 10:31:01 +05:00
Alex Ant faa5a862cf delete repo skills 2026-04-11 00:44:16 +05:00
Alex Ant b84e1fda36 chore(release): publish 2026-04-11 00:43:41 +05:00
Alex Ant ddad66d4ea chore(release): publish 2026-04-11 00:42:24 +05:00
Alex Ant 16a25fdf96 fix 2026-04-11 00:41:23 +05:00
Alex Ant 57de643350 Merge branch 'dev' of github.com:coopenomics/mono into dev 2026-04-11 00:36:05 +05:00
Alex Ant 3bb61d0258 update blago cli skills 2026-04-11 00:35:35 +05:00
coopops 108d358ddc [562-9] Авторасширение поля описания в диалоге создания задачи
[@ant]

Made-with: Cursor
2026-04-10 19:26:56 +00:00
coopops ca75a0ac33 [562-4] Отображение и редактирование меток задач Capital (сайдбар и списки)
[@ant]

Made-with: Cursor
2026-04-10 19:01:12 +00:00
coopops 5297f0b8a8 [562-7] Фокус на первом поле при открытии CreateDialog
[@ant]

Made-with: Cursor
2026-04-10 18:51:43 +00:00
Alex Ant c17d782b6b .cursor skills 2026-04-10 23:22:51 +05:00
Alex Ant c58dc84dee chore(release): publish 2026-04-10 23:17:46 +05:00
Alex Ant 0015818e13 chore(release): publish 2026-04-10 23:15:14 +05:00
Alex Ant 5f97c364ca blago-cli linter + .gitgnore for _blago 2026-04-10 23:01:02 +05:00
Alex Ant 406ebd2b16 linter fix 2026-04-10 21:35:09 +05:00
Alex Ant d9451adb53 chore(release): publish 2026-04-10 20:53:07 +05:00
Alex Ant cc0e40a2fc [562-20] Суффикс id в заголовках проекта/задачи и копирование по клику
[@ant]

Made-with: Cursor
2026-04-10 20:50:11 +05:00
Alex Ant 4e6817c4ce chore(release): publish 2026-04-10 18:36:40 +05:00
Alex Ant eb4052922b blago-cli commands ignore list & title padding on desktop 2026-04-10 18:35:09 +05:00
Alex Ant 980589152e [562-19] Учёт времени: reconcile билетов при смене estimate в capital
[@ant]

Made-with: Cursor
2026-04-10 18:33:50 +05:00
Alex Ant 31e9c16cf5 [562-16] Дробный estimate и учёт времени до коммита (capital)
[@ant]

Made-with: Cursor
2026-04-10 18:00:32 +05:00
Alex Ant 79f72624d1 chore(release): publish 2026-04-10 14:21:15 +05:00
Alex Ant f4daf52a79 chore(release): publish 2026-04-10 14:20:26 +05:00
Alex Ant 6229697faa [562-18] Capital desktop: шапка title/path, мобильный «Подробнее», компактный path и инпуты
[@ant]

Made-with: Cursor
2026-04-10 14:19:12 +05:00
Alex Ant fd564c7098 chore(release): publish 2026-04-10 13:15:53 +05:00
Alex Ant d64d68d340 chore(release): publish 2026-04-10 13:13:17 +05:00
Alex Ant 853f9bfc1c blago-cli SKILLS & bmad & matrix component notification 2026-04-10 13:11:45 +05:00
Alex Ant be93fd84a5 [724-1] Добавить поле memo для создания ручных заметок по встрече
[@ant | 8a7ca7e8f9dcc399d5f17c95931a892ce00469df9d07204096951d2ee53ef6c0]
2026-04-09 19:49:57 +05:00
Alex Ant 96b96916f8 chore(release): publish 2026-04-08 22:04:03 +05:00
Alex Ant 15e3471400 chore(release): publish 2026-04-08 22:03:24 +05:00
Alex Ant 386868fc97 Editor preview mermaid fix 2026-04-08 22:01:32 +05:00
Alex Ant 9c9e5b3d0a blago-cli create tasks immediatly 2026-04-08 21:50:29 +05:00
Alex Ant 2a2152d13d chore(release): publish 2026-04-08 21:16:52 +05:00
Alex Ant 5927b89863 chore(release): publish 2026-04-08 21:15:53 +05:00
Alex Ant 1744943636 update pull communications 2026-04-08 21:06:40 +05:00
Alex Ant 89cc1f634d [562-17] desktop: Crepe Mermaid-превью, темы, вёрстка кода и таблиц [@ant | a0dcedc90764e9ae153e022d931d8f824b3362e772fda8fca3329057145aeb04]
Editor.vue: overflow/min-width для ProseMirror, таблиц, CodeMirror; тема Crepe; copy/preview RU; crepeMermaidRenderPreview. WrappedEditor, IssuePage, EditRequirementPanel: min-w-0 для flex.

Made-with: Cursor
2026-04-08 21:05:40 +05:00
Alex Ant f8b7f9dded chore(release): publish 2026-04-08 15:35:14 +05:00
Alex Ant c1344fe5f1 chore(release): publish 2026-04-08 15:34:10 +05:00
Alex Ant 4ab084859d update 2026-04-08 15:33:29 +05:00
Alex Ant c7f0faf4ba [0] blago-cli: pull messages/meetings, курсоры, staging без push артефактов | ant 6f4c87ec41525ba909cfbf906ed5364245e6e2db2742a4b4d13ba986c48f12b0
pull-communication, sync-entity-file, pull-only-paths, restore; лимит транскрипций 100; formatThrownValue.

Made-with: Cursor
2026-04-08 15:10:15 +05:00
Alex Ant e7185f62da [0] SDK Zeus: запросы переписки ChatCoop по проектам | ant 6f4c87ec41525ba909cfbf906ed5364245e6e2db2742a4b4d13ba986c48f12b0
Селекторы projectCommunication, queries list/get rooms и сообщений.

Made-with: Cursor
2026-04-08 15:10:01 +05:00
Alex Ant ac69301a82 [0] ChatCoop GraphQL переписки проектов и гард active-user | ant 6f4c87ec41525ba909cfbf906ed5364245e6e2db2742a4b4d13ba986c48f12b0
Resolver project-communication, DTO, ActiveUserStatusGuard, schema.gql и zeus codegen.

Made-with: Cursor
2026-04-08 15:09:52 +05:00
Alex Ant 537c3b8454 blago-cli update 2026-04-08 11:26:36 +05:00
Alex Ant 947547b4d8 chore(release): publish 2026-04-06 22:11:11 +05:00
Alex Ant 29133c0e37 chore(release): publish 2026-04-06 18:52:12 +05:00
Alex Ant 8850b7a9f6 normalize user emails 2026-04-06 18:50:37 +05:00
Alex Ant a9b62fafa7 chore(release): publish 2026-04-06 15:54:47 +05:00
Alex Ant 05de97d20c chore(release): publish 2026-04-06 15:50:03 +05:00
Alex Ant 8106b089c0 chat coop event calendar notifier & bugfix for novu email sender 2026-04-06 15:48:01 +05:00
Alex Ant 986146d5a1 chore(release): publish 2026-04-05 16:51:11 +05:00
Alex Ant 939b8a9dee chore(release): publish 2026-04-05 16:49:26 +05:00
Alex Ant 8a12e1b50a blago-cli MVP release 2026-04-05 16:46:58 +05:00
Alex Ant 17ddefd9a2 chore(release): publish 2026-04-04 14:50:58 +05:00
Alex Ant 27470da264 chore(release): publish 2026-04-04 14:06:18 +05:00
Alex Ant f7404f37c0 down log level on subscription check 2026-04-04 14:03:19 +05:00
Alex Ant 41e6a6986b novu: quotes in subject title deletion 2026-04-04 14:00:49 +05:00
Alex Ant 63e062d8f8 meet css refactoring 2026-04-04 13:53:33 +05:00
Alex Ant 6bc8d793f8 notifications for meet with details 2026-04-04 01:38:54 +05:00
Alex Ant 94ab81fa64 controller meets v2 2026-04-04 00:13:22 +05:00
Alex Ant 333553d283 chore(release): publish 2026-04-02 00:38:32 +05:00
Alex Ant 4b4e88102e chore(release): publish 2026-04-02 00:19:41 +05:00
Alex Ant aa18df8724 milkdown editor 2026-04-02 00:18:14 +05:00
Alex Ant 250193a881 calendar timezone fix 2026-04-01 14:08:41 +05:00
Alex Ant c890376c5d scrub sensitive data from sentry log 2026-03-31 13:26:11 +05:00
Alex Ant 4050da5b13 chore(release): publish 2026-03-31 13:12:50 +05:00
Alex Ant b5b4769116 chore(release): publish 2026-03-31 13:11:24 +05:00
Alex Ant 943714cb47 sync delay on capital extension & correct sync removed entities from github 2026-03-31 13:10:02 +05:00
Alex Ant ac5e679eea chore(release): publish 2026-03-31 09:42:46 +05:00
Alex Ant a3e2cd892f prohibit delete project with components 2026-03-31 09:41:12 +05:00
Alex Ant 68066a5321 sync deletion projects, components, issues from db to github 2026-03-30 13:04:04 +05:00
Alex Ant ce93a90e89 fix project deletion 2026-03-30 12:26:59 +05:00
Alex Ant ac8a0c4466 xss skip for some routes 2026-03-30 12:02:39 +05:00
Alex Ant 86a4bdc999 chore(release): publish 2026-03-29 18:19:31 +05:00
Alex Ant 4636ced3a4 chore(release): publish 2026-03-29 17:52:31 +05:00
Alex Ant 646b1c90a2 calendar of events 2026-03-29 17:50:44 +05:00
Alex Ant 48ecb49a59 calendar of events 2026-03-28 21:09:57 +05:00
Alex Ant 396e17f698 chore(release): publish 2026-03-27 18:07:43 +05:00
Alex Ant c4230233bb chatcoop safe room storage 2026-03-27 17:56:15 +05:00
Alex Ant d14c0890fa unencrypt participant room & save coop rooms to a repository 2026-03-27 14:25:00 +05:00
Alex Ant d9f5017ade chatcoop -> matrix project requirements sync 2026-03-27 13:35:38 +05:00
Alex Ant 553a2e68cc chore(release): publish 2026-03-26 17:36:27 +05:00
Alex Ant 0de793bb80 chore(release): publish 2026-03-26 17:35:14 +05:00
Alex Ant 7f8c6d6dc1 ignore messages and transcriptions on sync from git 2026-03-26 17:34:23 +05:00
Alex Ant 880b52ed52 chore(release): publish 2026-03-26 16:19:46 +05:00
Alex Ant b33c3530b0 down log level for message sync 2026-03-26 16:18:33 +05:00
Alex Ant 705ecb8f18 chore(release): publish 2026-03-26 14:37:52 +05:00
Alex Ant cd812f2a3a not sync the messages and meetings from github 2026-03-26 14:33:19 +05:00
Alex Ant 842d104431 chore(release): publish 2026-03-26 14:03:30 +05:00
Alex Ant c031d3e34c add secretary to the rooms after they created 2026-03-26 14:02:10 +05:00
Alex Ant 30a7fe25d9 chore(release): publish 2026-03-26 12:29:33 +05:00
Alex Ant 7e6756f99e @coopenomics/inter package & messages & calls github sync 2026-03-26 12:28:31 +05:00
Alex Ant 9621d38ddd matrix: room message history 2026-03-26 10:20:58 +05:00
Alex Ant bffb3a95fc chore(release): publish 2026-03-25 23:49:05 +05:00
Alex Ant c9324271f6 transcriptions in project rooms 2026-03-25 23:46:20 +05:00
Alex Ant 2eb006fa70 secretary transcription service 2026-03-25 21:03:17 +05:00
Alex Ant b803016077 chore(release): publish 2026-03-24 21:12:03 +05:00
Alex Ant ecab9a4be1 chore(release): publish 2026-03-24 21:05:34 +05:00
Alex Ant 029b0fd08a update workflow 2026-03-24 21:04:05 +05:00
Alex Ant 2cd85b7440 chore(release): publish 2026-03-24 19:47:45 +05:00
Alex Ant c3b0ec99cd chore(release): publish 2026-03-24 19:46:01 +05:00
Alex Ant 59c207ef29 publish docs fix 2026-03-24 19:44:40 +05:00
Alex Ant 0cf8b64a4b chore(release): publish 2026-03-24 18:37:30 +05:00
Alex Ant 69ab3f9770 upgrade node 2026-03-24 18:36:22 +05:00
Alex Ant 3f08b6949e chore(release): publish 2026-03-24 18:22:44 +05:00
Alex Ant 17e3e8ad63 chore(release): publish 2026-03-24 18:18:52 +05:00
Alex Ant ceb6b63e2d fast buttons for capital extension 2026-03-24 18:15:25 +05:00
Alex Ant e377d40104 create blagorost project -> create matrix room -> invite participants 2026-03-24 17:51:26 +05:00
Alex Ant de8d33e715 create matrix room on create capital project 2026-03-24 15:09:31 +05:00
Alex Ant 6864518bd9 chore(release): publish 2026-03-23 23:53:45 +05:00
Alex Ant b75f0b92a1 disable NOVU blocker 2026-03-23 23:52:52 +05:00
Alex Ant 2e32ed7fd1 chore(release): publish 2026-03-23 22:55:31 +05:00
Alex Ant 30d2333cad remove moment-legacy & upgrade express 2026-03-23 22:54:34 +05:00
Alex Ant 1271ccce77 chore(release): publish 2026-03-23 20:35:44 +05:00
Alex Ant 82d4bb34b7 upgrade to vite 8 2026-03-23 20:34:35 +05:00
Alex Ant f8ca89ada6 what the fuck 2026-03-23 17:44:50 +05:00
Alex Ant f85fa7d786 chore(release): publish 2026-03-23 15:54:29 +05:00
Alex Ant 45c91ccc7f MERMAID & DRAWIO integration 2026-03-23 15:52:27 +05:00
Alex Ant c17efc489c chore(release): publish 2026-03-23 00:42:42 +05:00
Alex Ant f7fffe2859 docs & bpmn story type 2026-03-23 00:40:49 +05:00
Alex Ant 62ab4ac379 chore(release): publish 2026-03-20 09:36:15 +05:00
Alex Ant 1744fab580 refactor: replace common.hpp with index.hpp in multiple contract headers and remove unused files 2026-03-20 09:35:38 +05:00
Alex Ant 01de5de342 chore(release): publish 2026-03-19 18:54:14 +05:00
Alex Ant d69451c9e6 chore(release): publish 2026-03-19 18:51:23 +05:00
Alex Ant fceb0bbb23 update memo in contract 2026-03-19 18:50:42 +05:00
Alex Ant f5a3e41190 chore(release): publish 2026-03-11 17:23:59 +05:00
Alex Ant 3113346b47 chore(release): publish 2026-03-11 17:08:55 +05:00
Alex Ant 0dc9691557 freedecision notification fix & contact display fix 2026-03-11 17:07:54 +05:00
Alex Ant cef796272c publish-docs with callback 2026-03-07 20:19:45 +05:00
Alex Ant dc45089908 chore(release): publish 2026-03-04 12:43:40 +05:00
Alex Ant 395bfa3bb3 chore(release): publish 2026-03-04 12:34:50 +05:00
Alex Ant c37e9a2a15 add blagorost agreement fields to contributor input process 2026-03-04 12:33:08 +05:00
Alex Ant 90b0204205 Merge branch 'audio-stream' into dev 2026-03-03 21:35:30 +05:00
Alex Ant 904218aa4c refactor(chatcoop): enhance secretary functionality and logging
- Updated the LiveKitWebhookController route to /v1/extensions/chatcoop/livekit-webhook.
- Improved error logging in MatrixApiService for better clarity.
- Added secretaryPasswordEncrypted field to the ChatCoopPlugin configuration.
- Implemented delayed initialization for the secretary in the ChatCoopPlugin.
- Enhanced the SecretaryAgentService to manage secretary access tokens and send messages on behalf of the secretary.
- Refactored message sending logic to fallback to admin credentials if secretary credentials are unavailable.
2026-02-28 20:26:49 +05:00
Alex Ant f08d1b68ab upgrade typedoc in sdk 2026-02-28 19:28:47 +05:00
Alex Ant cfd7c72fd2 upgrade typedoc 2026-02-28 19:26:43 +05:00
Alex Ant 509471c97d chore(release): publish 2026-02-28 19:21:54 +05:00
Alex Ant f748d14d25 chore(release): publish 2026-02-28 18:39:30 +05:00
Alex Ant ae2bdb48cf fix removed extensions methods 2026-02-28 18:38:52 +05:00
Alex Ant dcc5a7a253 chore(release): publish 2026-02-28 17:39:57 +05:00
Alex Ant 25ed795ff6 refactor(soviet): remove vote copy mutations, queries, and selectors
- Deleted createVoteCopy, deactivateVoteCopy, and deleteVoteCopy mutations.
- Removed getMyVoteCopySettings and getWhoCopiesToMe queries.
- Eliminated voteCopySettingSelector and its related exports.
- Cleaned up index files for mutations and queries to reflect these removals.
2026-02-28 17:38:53 +05:00
Alex Ant 431db5f7d4 chore(release): publish 2026-02-28 17:26:31 +05:00
Alex Ant 24253f189c Merge branch 'dev' into testnet 2026-02-28 17:25:51 +05:00
Alex Ant a59192d95d bugfixes 2026-02-28 16:16:47 +05:00
Alex Ant d734ed3677 cherry-pick and replace. does not works yet after update 2026-02-28 15:31:34 +05:00
Cursor Agent 1379ebec06 rollback to 2026-02-28 12:57:15 +05:00
Cursor Agent c5eded9f7b feat(reports): add Desktop UI extension and register reports in backend
- Create reports extension for desktop with ReportsPage
- ReportsPage shows report schedule, generation dialog, XML result viewer
- Download generated XML files directly from browser
- Register reports in extensions-registry.ts on desktop side
- Register ReportsExtensionModule in backend AppRegistry
- Extension available for chairman role
2026-02-28 11:56:27 +05:00
Cursor Agent 68c2efdb5c feat(reports): rewrite FNS report generators with XSD-compliant XML
- Rewrite BuhotchGenerator with proper Баланс and ЦелИсп sections per XSD
- Rewrite Ndfl6Generator with ОКТМО, РасчСумНал zero structure
- Create individual generators: RsvGenerator, PsvGenerator, DusnGenerator, Fss4Generator, UvVznosyGenerator, UusnGenerator
- Add xml-utils.ts with shared XML building helpers
- Update ReportInput interface with oktmo, address, signerSnils fields
- Add OrganizationDataInputDTO for frontend data input
- Integrate LedgerInteractor for real balance data in reports
- Add 48 unit tests covering all 8 generators
2026-02-28 11:56:18 +05:00
Cursor Agent 00a8461b5b docs: update TASKS.md — reports 11/15 subtasks complete 2026-02-25 23:07:54 +00:00
Cursor Agent 7154c7f0e0 feat(reports): complete FNS/FSS report generation system
Report types (8):
- Бухгалтерский баланс (yearly, with ledger data: accounts 51, 80, 86)
- 6-НДФЛ (quarterly, zero)
- РСВ (quarterly, zero)
- ПСВ (monthly, zero)
- ДУСН (yearly, zero)
- 4-ФСС/ЕФС-1 (quarterly, zero)
- Уведомление о взносах (monthly, zero)
- Уведомление УСН (quarterly, zero)

Architecture:
- ReportRegistryService: factory pattern for report generators
- IReportGenerator interface: generate() + generateFileName()
- BuhotchGenerator: full balance sheet with ledger integration
- Zero report generator factory for all other types
- GraphQL: getAvailableReports query + generateReport mutation
- Deadline checker: isGenerationAvailable()
- XML in windows-1251 with Cyrillic tags per FNS standards
2026-02-25 23:04:18 +00:00
Cursor Agent 0f07666aeb feat(reports): extension skeleton + XSD schemas for all FNS reports
XSD schemas:
- NO_BUHOTCH — Бухгалтерский баланс (годовой)
- NO_NDFL6.2 — 6-НДФЛ (квартальный)
- NO_PERSSVFL — ПСВ (ежемесячный)
- NO_RASCHSV — РСВ (квартальный)
- NO_USN — ДУСН (годовой)
- UT_UVISCHSUMNAL — Уведомление о взносах (ежемесячный)

Extension structure: domain, infrastructure, application layers
2026-02-25 22:50:40 +00:00
Cursor Agent 489dc482e8 docs: TASKS.md — plan for FNS reports system 2026-02-25 22:48:34 +00:00
Cursor Agent 55c4759780 fix: resolve all lint/tsc errors in desktop
- DocumentSearchDialog: v-html on div instead of component, fix onSearch type
- Process API: cast data to any for updateProcessTemplate mutation
- quasar.config: overlay: false for dev (pre-existing TS warnings)
2026-02-25 22:40:16 +00:00
Alex Ant 16b4fe0080 add reports-standarts 2026-02-26 03:13:19 +05:00
Cursor Agent 9cd995c5f2 fix(capital/processes): simplify issue ID generation for process tasks 2026-02-25 21:59:10 +00:00
Cursor Agent e60d6a5d67 fix(capital/processes): fix TS errors — IssueIdGenerationService method name, IBaseDatabaseData fields 2026-02-25 21:57:14 +00:00
Cursor Agent b274af05c3 docs: update TASKS.md — process system 8/9 subtasks done 2026-02-25 21:53:19 +00:00
Cursor Agent 40e725f2ed feat(capital/processes): frontend — ProcessesPage with Vue Flow
- ProcessesPage with sidebar (process list) + Vue Flow canvas
- Process entity: API client, types
- Sidebar: list of templates, create dialog, select/deselect
- Vue Flow: nodes (steps) with edges (connections)
- Step adding, edge creation via drag
- Save/activate/delete templates
- Start nodes highlighted green
- Registered in capital extension install.ts as 'Процессы'
- Role-based: edit for chairman/member, view for all
2026-02-25 21:52:28 +00:00
Cursor Agent 0f091eefc9 feat(capital/processes): full backend CRUD + execution engine
- ProcessService: create/update/delete templates, start/complete process instances
- ProcessResolver: GraphQL mutations & queries with role-based access
  - chairman/member: create/update/delete templates
  - chairman/member/user: start processes, complete steps
- Repositories: TypeORM with CAPITAL_DATABASE_CONNECTION
- DTOs: ProcessTemplate, ProcessInstance, ProcessStep, ProcessEdge
- Auto-creates issues when steps become active
- Tracks step completion and cascading activation
- Process completes when all terminal steps done
- Registered in capital-database.module and capital-extension.module
2026-02-25 21:47:17 +00:00
Cursor Agent 2b00c58e9b feat(capital/processes): data model foundation
TypeORM entities:
- ProcessTemplateTypeormEntity: template with steps (Vue Flow nodes) and edges
- ProcessInstanceTypeormEntity: running instance with step_states

Domain entities:
- ProcessTemplateDomainEntity with ProcessStepTemplate and ProcessEdge
- ProcessInstanceDomainEntity with ProcessStepState

Enums:
- ProcessTemplateStatus: draft/active/archived
- ProcessInstanceStatus: running/completed/cancelled
- ProcessStepStatus: pending/active/completed/cancelled

Vue Flow installed for desktop (process designer)
2026-02-25 21:31:52 +00:00
Cursor Agent 6d9681fb8a docs: update TASKS.md with process system plan 2026-02-25 21:27:14 +00:00
Cursor Agent acc4d27677 fix(search): index documents on blockchain newsubmitted event, not on generation
- Removed indexing from GeneratorInfrastructureService.generateDocument()
- Created SearchEventService listening to action::soviet::newsubmitted
- Documents are indexed only when signed and submitted to blockchain
- Fetches full document from MongoDB by hash, indexes into OpenSearch
2026-02-25 21:26:26 +00:00
Cursor Agent ffe581a92b feat(search): полностью рабочая поисковая система документов
Визуально протестировано:
- Поиск 'кошелёк' → 1 результат с подсветкой КОШЕЛЕК
- Поиск 'соглашение' → 4 результата с fuzzy matching (соглашения, соглашается, согласию)
- Кнопка Поиск в header actions на страницах документов
- OpenSearch 2.18.0 с аутентификацией (admin/password)
- Zeus types перегенерированы из schema.gql
- /etc/hosts: opensearch → 127.0.0.1
2026-02-25 21:15:42 +00:00
Cursor Agent 6e643515ce fix(search): OpenSearch 2.18.0 with auth, Zeus types regenerated
- OpenSearch 2.18.0 with OPENSEARCH_INITIAL_ADMIN_PASSWORD
- SearchRegistryService: auth + SSL support
- Zeus types regenerated from schema.gql (features, searchDocuments, SearchResult)
- SDK selector validation re-enabled
- Reverted System API hack — proper Zeus types now handle features
2026-02-25 21:03:07 +00:00
Cursor Agent 1cc7aca53f fix(search): TS catch types, OpenSearch 2.11.1 compatibility
- Fix 'e' is of type 'unknown' in catch blocks
- Downgrade OpenSearch to 2.11.1 (no admin password required)
- docker-compose.yaml updated
2026-02-25 20:19:52 +00:00
Cursor Agent e5111622a6 refactor(search): фабричный SearchRegistry + header actions pattern
Backend:
- SearchRegistryService: универсальный фабричный движок поиска
  - registerIndex(): регистрация индексов с маппингами
  - index(): индексация любых данных
  - search(): generic поиск по любому индексу
- DocumentSearchService: регистрирует индекс 'documents' через registry
- Разделение: registry (универсальный) vs document search (специфичный)

Desktop:
- SearchHeaderAction: компонент для header actions system
- Убран прямой SearchButton из MainHeader
- UserDocumentsPage: registerAction через useHeaderActions
- ListOfDocumentsPage (совет): registerAction через useHeaderActions
- Действие появляется ТОЛЬКО на страницах документов
- Скрыто если features.search=false
2026-02-25 20:10:44 +00:00
Cursor Agent 99b98cb5c9 docs: update TASKS.md with search system progress 2026-02-25 19:59:38 +00:00
Cursor Agent 20447cfb46 feat(search): SDK query + Desktop search UI components
SDK:
- searchDocuments query with input/output types
- features selector in SystemInfo (search flag)

Desktop:
- DocumentSearchDialog: full-text search modal with debounced input
- SearchButton: conditional button (shown only if features.search=true)
- Header integration: SearchButton next to NotificationCenter
- UserDocumentsPage: SearchButton on documents registry page
- Graceful: hidden when search feature disabled
2026-02-25 19:55:50 +00:00
Cursor Agent 723a1813c9 feat(search): OpenSearch integration in controller
- SystemFeatures: new features field in SystemInfo with search flag
- OpenSearchService: index management, document indexing, full-text search
- SearchResolver: GraphQL searchDocuments query with auth
- Auto-indexing: documents indexed on generation via GeneratorService
- Graceful degradation: works without OpenSearch (features.search=false)
- SearchModule + SearchInfrastructureModule registered in app.module
2026-02-25 19:44:59 +00:00
Cursor Agent 04d52a0631 feat(search): add OpenSearch to docker-compose and reboot
- OpenSearch 2.18.0 single-node, security disabled for dev
- Volume opensearch_data for persistence
- Reboot script clears opensearch on restart
- Controller .env-example: OPENSEARCH_NODE, OPENSEARCH_ENABLED
2026-02-25 19:26:13 +00:00
Cursor Agent 097d18cd56 docs: add TASKS.md with progress tracking 2026-02-25 19:22:58 +00:00
Cursor Agent 5043995d14 docs: добавлены AGENTS.md для 6 компонентов (factory, boot, parser, sdk, cooptypes, notifications)
Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 19:02:40 +00:00
Cursor Agent 804cfc8b72 docs(desktop): добавлен AGENTS.md — справочный документ по архитектуре фронтенда
Подробный документ на русском языке, описывающий:
- Feature Sliced Design (FSD) архитектуру и правило зависимостей слоёв
- Систему расширений (extensions): архитектура, регистрация, загрузка
- Все 8 расширений с описанием ролей и страниц
- Desktop Store, Session Store, System Store
- Процессы инициализации и их последовательность
- Навигационные гварды и ролевой доступ
- SSR vs SPA: известная проблема с Pinia-сериализацией
- Widget-режим, DecisionFactory, RequireAgreements
- Паттерны кода и правила для AI-агентов

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 18:56:03 +00:00
Cursor Agent a0dc6f3333 docs(controller): добавлен AGENTS.md — архитектура, расширения, паттерны
Подробная документация для AI-агентов:
- Обзор чистой архитектуры (domain → infrastructure → application)
- Дерево директорий с описанием каждого уровня
- Описание всех 10 расширений (chairman, capital, chatcoop и др.)
- Блокчейн-адаптеры и смарт-контракты EOSIO
- Система аутентификации JWT + RolesGuard
- Платёжный шлюз (yookassa, sberpoll, qrpay)
- Генерация документов через @coopenomics/factory
- TypeORM-сущности (23+ таблиц)
- Конфигурация и переменные окружения

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 18:48:03 +00:00
Cursor Agent a53957271e feat(setup): профессиональный установщик с 3 режимами
- Разработка: генерация .env, сборка библиотек и контрактов
- Тестовая сеть: фронтенд подключается к testnet API
- Продакшен: генерация конфигурации для mainnet
- Красивый CLI с inquirer, ora spinners, цветной вывод
2026-02-25 18:39:18 +00:00
Cursor Agent abae483dd3 docs: обновлены README и описания всех компонентов на русском языке
- Корневой README обновлён с актуальной структурой и командами
- 13 компонентных README с единым стилем: описание, фичи, скрипты, архитектура, тесты
- Обновлены description в package.json всех компонентов
- Новые README для cleos и setup (ранее отсутствовали)

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 18:31:36 +00:00
Cursor Agent 4418e09211 docs: создание профессиональных README.md для 6 компонентов монорепозитория
- cooptypes: типы и интерфейсы экосистемы с подробной архитектурой
- sdk: TypeScript SDK с быстрым стартом и описанием классов
- notifications: библиотека уведомлений с таблицей 21 workflow
- contracts: смарт-контракты EOSIO с описанием чистой архитектуры
- migrator: утилита миграций с жизненным циклом
- docs: документация MkDocs Material с инструкцией по синхронизации

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 18:30:06 +00:00
Cursor Agent ca79457c19 docs: add professional Russian-language README files for 7 components
- boot: CLI blockchain initialization utility
- cleos: EOSIO cleos wrapper with wallet container
- controller: NestJS GraphQL API backend
- desktop: Vue 3 + Quasar cooperative workspace
- factory: legal document generator library
- parser: blockchain indexer via SHiP
- setup: interactive setup wizard

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 18:25:53 +00:00
Cursor Agent d2cd947b9c fix(tests): add sleep in high precision test to prevent duplicate tx
Add sleep(200) between refreshSegment calls in loops
and sleep(500) between commitToResult calls

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 18:13:12 +00:00
Cursor Agent ea28285639 docs: add test running instructions to AGENTS.md
Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 17:58:22 +00:00
Cursor Agent 6174ddea9a fix(tests): add sleep before investor refreshSegment to prevent duplicate transaction
The refreshSegment calls for investors duplicate the ones from the
'вносим результаты' loop earlier in the test suite. Without a delay,
the TAPOS block reference may be identical, causing EOSIO to reject
the transaction as a duplicate. This follows the existing pattern
used elsewhere in the test file (e.g. line 720).

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 17:57:22 +00:00
Cursor Agent ce56adc3c8 feat(tests): boot capital 58/60, integration script
Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 17:44:23 +00:00
Cursor Agent 59334bb13a feat(tests): add integration test runner script
- scripts/run-integration-tests.sh with configurable host/ports
- SDK tests: login, extensions, branches, systemInfo
- Notifications: 7 smoke tests for exports and workflows
- Root test pipeline: test:unit -> test:component -> test:integration

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 17:27:18 +00:00
Cursor Agent 21cd1f5217 feat(tests): add SDK, notifications tests; fix test scripts
- SDK: 4 integration tests (login, extensions, branches, systemInfo)
- Notifications: 7 smoke tests (exports, workflows, config helpers)
- Fix vitest watch mode in sdk package.json
- Add vitest to notifications devDependencies
- Update root test pipeline: unit -> component -> integration

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 17:18:56 +00:00
Cursor Agent 515df53c96 fix(tests): fix 5 failing factory tests — 85/85 passing
1. test/index.test.ts: Add block_num: 1 to ParticipantApplication tests.
   Root cause: getCurrentBlock() returns 0 with SKIP_BLOCK_FETCH=TRUE,
   and the source code check 'if (data.block_num)' treats 0 as falsy,
   skipping the signature DB lookup during document regeneration.

2. test/blagorost.test.ts: Add udata records in beforeAll.
   Root cause: udata.test.ts runs before blagorost.test.ts and its
   beforeEach clears the entire udatas collection, removing records
   inserted by the global preLoading() setup.

3. test/udata.test.ts: Insert versioned records directly into MongoDB
   with incrementing block_num values (10, 20, 30, 40).
   Root cause: getCurrentBlock() returns 0 for all saves, making all
   versions have identical block_num. Since getOne sorts by block_num
   desc, ties are resolved non-deterministically by MongoDB.

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 17:02:19 +00:00
Cursor Agent cbf7f48c44 feat(tests): factory 80/85 passing — add authorize, signatures, udata setup
- Add authorize action mocks with document data for decisions
- Add signatures collection setup for participant applications
- Add Udata records for capital/blagorost/generator agreements
- Add decision with accepted status for meet 301 tests
- Enable fileParallelism: false to prevent test data races
- Remaining 5: 3 signature lookup issues, 1 blagorost udata, 1 udata versioning

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 16:29:54 +00:00
Cursor Agent ed37aeb615 fix(tests): fix DB-backed action mocks, factory 63/85 passing
- Fix action query format (account/name vs action.account)
- Remaining 22 tests need Udata service or full signatures setup
- These are integration-level tests requiring controller running

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 15:40:26 +00:00
Cursor Agent ea89558696 feat(tests): add DB-backed mocks for factory tests — 59/85 passing
- Add draft table/translation mocks that read from MongoDB
- Add cooperative table mock for registrator/soviet data
- Add fallback DB actions mock
- Fix translation lookup: map registry_id -> internal id for draft_id
- Support SOURCE=local for local template resolution
- Remaining 26 tests need capital/blagorost flow setup (Udata, votes)

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 15:35:30 +00:00
Cursor Agent c0bad75a37 docs: update TEST_PLAN.md with detailed status and strategy
Factory tests need mocks for draft templates and cooperative data.
Boot tests need full reboot before running.
Detailed plan for all components.

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 15:01:49 +00:00
Cursor Agent bdc227f110 feat(tests): add unified pnpm run test pipeline
- Root: pnpm run test (test:unit + test:integration)
- test:unit: cooptypes (4 smoke tests) + parser (3 config tests)
- test:integration: boot capital.test (60 blockchain tests)
- boot: add vitest config and test scripts
- cooptypes/parser: fix vitest watch mode -> vitest run
- controller: test script placeholder (tests via boot)
- Update TEST_PLAN.md

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 14:47:21 +00:00
Cursor Agent a9c3a1b6de fix(tests): cleanup cooptypes, parser, controller tests
- cooptypes: replace empty test with smoke test of exports (4 tests)
- parser: replace commented-out test with config smoke test (3 tests)
- controller: remove all outdated pre-NestJS integration and unit tests
- factory: make mongoUri configurable via env vars
- Add TEST_PLAN.md for tracking test implementation

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 14:38:59 +00:00
Cursor Agent f0e7b0b63a docs: finalize AGENTS.md with complete Cloud setup instructions
Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 14:21:29 +00:00
Cursor Agent a709e2f1e3 fix(security): update vulnerable deps in desktop, boot, factory
- desktop: axios, dompurify, express
- boot: axios, mongoose
- factory: axios, mongodb

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 14:08:47 +00:00
Cursor Agent 3a34bd74db fix(security): downgrade express to 4.21.2 (v5 has breaking changes with path-to-regexp)
Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 14:07:02 +00:00
Cursor Agent b755cb715a fix(security): update vulnerable dependencies in controller
CRITICAL fixes:
- mongoose 8.5.2 -> 9.2.2
- jspdf 2.5.1 -> 4.2.0
- jsonwebtoken 8.5.1 -> 9.0.3

HIGH fixes:
- express 4.17.1 -> 5.2.1
- axios 1.6.2 -> 1.13.5
- nodemailer 6.3.1 -> 8.0.1
- validator 13.0.0 -> 13.15.26
- ws 8.18.0 -> 8.19.0
- helmet 4.1.0 -> 8.1.0
- compression 1.7.4 -> 1.8.1
- moment 2.24.0 -> 2.30.1
- morgan 1.9.1 -> 1.10.1
- nodemon 2.0.0 -> 3.1.14
- supertest 6.0.1 -> 7.2.2
- cross-spawn 7.0.6 (added)

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 14:02:57 +00:00
Alex Ant 42753fae0a update 2026-02-25 18:25:42 +05:00
Alex Ant d8b8fa2d6e update 2026-02-25 18:14:18 +05:00
Cursor Agent a75277e0b8 docs: update AGENTS.md with docker networking and reboot instructions
Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 13:06:05 +00:00
Alex Ant f95b83674b update 2026-02-25 17:38:55 +05:00
Cursor Agent bb13e780af fix: correct SHiP port mapping 8070:8070 (was 8070:8080)
state-history-endpoint in config.ini listens on container port 8070,
not 8080. Fixed mapping so parser can connect via ws://127.0.0.1:8070

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 10:33:26 +00:00
Cursor Agent 6e80d5187c docs: document SSR hydration issue in desktop dev mode
Root cause: Pinia serializes Vue component objects from extension
routes into __INITIAL_STATE__. After hydration, components are
plain objects without render/setup functions. Production SSR build
works fine. Dev workaround: use SPA mode (quasar dev without --mode ssr).

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 10:23:15 +00:00
Cursor Agent db9b704d1d feat: add dev services to docker-compose, fix SHiP port, CHAIN_ID, postgres version
- docker-compose.yaml: add coopback, cooparser, desktop services for dev mode
- docker-compose.yaml: add SHiP port 8070, pin postgres:16
- components/desktop/.env-example: fix CHAIN_ID to match local blockchain
- components/parser/.env-example: fix SHIP port to 8070
- AGENTS.md: comprehensive dev environment instructions
- Remove docker-compose.override.yaml (changes merged into main file)

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 10:23:15 +00:00
Cursor Agent 65a2b5361c chore: add AGENTS.md and docker-compose.override for dev environment setup
- AGENTS.md: development instructions for Cursor Cloud agents
- docker-compose.override.yaml: pin postgres:16 (postgres:latest v18+ breaks with current volume config)

Co-authored-by: Alex Ant <dacom-dark-sun@users.noreply.github.com>
2026-02-25 10:22:23 +00:00
Alex Ant 7bca73cd7b chore(release): publish 2026-02-25 10:22:23 +00:00
Alex Ant 59383014be chore(release): publish 2026-02-25 10:22:23 +00:00
Alex Ant 60a5296f5f notification center repair 2026-02-25 10:22:23 +00:00
Alex Ant eb4fe333a7 chore(release): publish 2026-02-25 10:22:23 +00:00
Alex Ant 8d06d6d817 chore(release): publish 2026-02-25 10:22:23 +00:00
Alex Ant b6afb536b6 expired decision & walletPage & 30 days for expiration & formatDateFromNow with local time 2026-02-25 10:22:23 +00:00
Alex Ant 790047fa8a chore(release): publish 2026-02-25 10:22:23 +00:00
Alex Ant baf55b6b6d chore(release): publish 2026-02-25 10:22:23 +00:00
Alex Ant 92d85244f1 update docker and packages 2026-02-25 15:20:11 +05:00
Alex Ant e0e8fef265 audio-stream 2026-02-23 20:21:46 +05:00
Alex Ant deb0f8344b chore(release): publish 2026-02-22 19:48:58 +05:00
Alex Ant ed135950eb openReplay ingest make throw proxy 2026-02-22 19:48:09 +05:00
Alex Ant ed7c547a06 chore(release): publish 2026-02-22 19:35:00 +05:00
Alex Ant 1a9f927c4c service-worker update fix & voting console.error log 2026-02-22 19:33:41 +05:00
Alex Ant 350af86b65 chore(release): publish 2026-02-22 14:17:08 +05:00
Alex Ant e136b73192 chore(release): publish 2026-02-22 13:08:00 +05:00
Alex Ant b6bf2fec21 notification center repair 2026-02-22 13:07:02 +05:00
Alex Ant 56daadbbca chore(release): publish 2026-02-21 21:06:27 +05:00
Alex Ant 7de26ec9a7 chore(release): publish 2026-02-21 20:19:13 +05:00
Alex Ant 7dbd3036df expired decision & walletPage & 30 days for expiration & formatDateFromNow with local time 2026-02-21 20:17:34 +05:00
Alex Ant 687085f9c7 chore(release): publish 2026-02-21 12:43:35 +05:00
Alex Ant 96cfc7e184 chore(release): publish 2026-02-21 12:42:06 +05:00
Alex Ant 0b26433b1a update 2026-02-21 12:40:54 +05:00
Alex Ant 4f06bb40f8 chore(release): publish 2026-02-21 12:34:00 +05:00
Alex Ant 46d571b65a update 2026-02-21 12:32:34 +05:00
Alex Ant 7da1bfd315 chore(release): publish 2026-02-21 12:15:08 +05:00
Alex Ant b30f47b5aa chore(release): publish 2026-02-21 12:13:59 +05:00
Alex Ant ccc6c7206c publish packages fix 2026-02-21 12:11:38 +05:00
Alex Ant a549f4cae0 chore(release): publish 2026-02-21 11:38:11 +05:00
Alex Ant 07c451ce22 fix npm publish-packages 2026-02-21 11:36:49 +05:00
Alex Ant 62da624369 chore(release): publish 2026-02-21 11:31:18 +05:00
Alex Ant a1a9b03180 chore(release): publish 2026-02-20 16:55:19 +05:00
Alex Ant e4c1d37c35 VideoPlayer and wallet fix 2026-02-20 16:54:06 +05:00
Alex Ant 42cacac256 chore(release): publish 2026-02-20 15:28:41 +05:00
Alex Ant 2816970327 update 2026-02-20 15:27:33 +05:00
Alex Ant 5744fcdcb2 chore(release): publish 2026-02-20 15:21:56 +05:00
Alex Ant 3c412b394d capital -> blagorost program type migration 2026-02-20 15:20:53 +05:00
Alex Ant 4e64cea373 update 2026-02-20 13:17:30 +05:00
Alex Ant db579db87f update 2026-02-20 13:01:59 +05:00
Alex Ant f612a918d9 update 2026-02-20 13:00:39 +05:00
Alex Ant 1a78e06a7a chore(release): publish 2026-02-20 12:49:32 +05:00
Alex Ant 374a98ffc3 update 2026-02-20 12:29:49 +05:00
Alex Ant d723e2e273 chore(release): publish 2026-02-20 11:39:36 +05:00
Alex Ant 41030171b5 update 2026-02-20 11:38:29 +05:00
Alex Ant aa31706bcc chore(release): publish 2026-02-20 11:26:19 +05:00
Alex Ant 4e3810493d update 2026-02-20 11:25:24 +05:00
Alex Ant eeb2db92ed chore(release): publish 2026-02-20 11:09:44 +05:00
Alex Ant 5a2930029b update 2026-02-20 11:09:15 +05:00
Alex Ant 2e9a73923b chore(release): publish 2026-02-20 10:19:35 +05:00
Alex Ant 97e67f8a88 fix workflow for package deployment 2026-02-20 10:18:47 +05:00
Alex Ant 074849af74 chore(release): publish 2026-02-20 09:30:23 +05:00
Alex Ant 6939783518 update 2026-02-20 09:30:01 +05:00
Alex Ant 260e48fa48 chore(release): publish 2026-02-20 09:26:36 +05:00
Alex Ant 52c4ef5df5 fix builder 2026-02-20 09:26:10 +05:00
Alex Ant 46b634e0fa chore(release): publish 2026-02-20 00:12:44 +05:00
Alex Ant a556c29a17 fix docker base image 2026-02-20 00:12:02 +05:00
Alex Ant bbc4f508b5 chore(release): publish 2026-02-19 23:10:26 +05:00
Alex Ant fe0243549a update .env-example 2026-02-19 23:07:12 +05:00
Alex Ant d9196ba650 add stub usernames 2026-02-19 22:53:22 +05:00
Alex Ant a0ea1fa392 pre-release 2026-02-19 22:01:50 +05:00
Alex Ant 195bcb4495 WTF 2026-02-19 16:41:15 +05:00
Alex Ant 929627a191 candidates page and contract calculation fix 2026-02-17 09:37:01 +05:00
Alex Ant 83a313b4b7 tests and fixes 2026-02-15 11:18:32 +05:00
Alex Ant f734bfb50f documents fixs & transcription page 2026-02-12 23:27:21 +05:00
Alex Ant 9efc22d195 chatcoop secretary transcriptor 2026-02-12 16:58:24 +05:00
Alex Ant bd3bef5fb0 chatcoop default room settings change 2026-02-12 11:29:32 +05:00
Alex Ant ddbe49e847 result submission 2026-02-12 10:43:48 +05:00
Alex Ant ed9bddec0b investors are invest to blagorost program directly, not to generation contract 2026-02-10 11:38:32 +05:00
Alex Ant 73a07eeb54 intellectual investments 2026-02-10 10:40:04 +05:00
Alex Ant 6e27aed804 registration process fixs 2026-02-09 23:44:34 +05:00
Alex Ant 5f955781a6 download document package button 2026-02-07 12:41:06 +05:00
Alex Ant c124f7310e some fixes 2026-02-07 12:09:43 +05:00
Alex Ant 73ffcae549 github sync subsystem on blagorost module 2026-02-06 21:15:13 +05:00
Alex Ant 80e55ba0be make requirements as documents and editor readonly mode 2026-02-06 13:46:35 +05:00
Alex Ant eecf955096 import contributors with some peculiarities 2026-02-06 11:16:29 +05:00
Alex Ant 6426db9a5d wallet sync and contributors import 2026-02-05 22:15:42 +05:00
Alex Ant bf4753cd09 gamification fix 2026-02-05 12:50:50 +05:00
Alex Ant a592eaf383 replace editor 2026-02-05 11:18:17 +05:00
Alex Ant 75d654cec3 feat: STORY-001 Исправить логику создания участников
Изменена логика создания Contributor с "при первом вкладе" на "при подтверждении доступа к проекту".
Теперь Contributor создается автоматически при одобрении appendix (confirmClearance).

Acceptance Criteria:
- Участник отображается в виджете сразу после подписания соглашения об участии
- Не требуется делать вклад для отображения в списке участников
- Логика создания Contributor изменена с "при первом вкладе" на "при подтверждении доступа"

Technical Changes:
- Добавлена логика создания Contributor в ClearanceManagementInteractor.handleConfirmClearance()
- Contributor создается со статусом APPROVED при подтверждении доступа
- Добавлены необходимые импорты и зависимости
- Обновлен статус спринта

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-02-04 11:42:55 +05:00
Alex Ant a18ed37600 blagorost test restore 2026-02-04 11:07:53 +05:00
Alex Ant 6747a8dfbc refactoring possible complete 2026-02-01 13:29:29 +05:00
Alex Ant 583dfb8126 before capital contract refactoring 2026-01-31 11:36:00 +05:00
Alex Ant bda31dd086 access violation bugfix with wharfkit rollback 2026-01-29 23:19:22 +05:00
Alex Ant 283af35f3b looking for access violation bug 2026-01-29 15:51:35 +05:00
Alex Ant 82564e2580 contract access violation bug fix | documents 2026-01-29 01:56:40 +05:00
Alex Ant fc6a9026e6 blagorost documents preparing 2026-01-27 23:00:27 +05:00
Alex Ant e1538bb5ab contract optional blagorost agreement on registration 2026-01-26 10:54:53 +05:00
Alex Ant d47db969ea refactoring vars on blagorost documents 2026-01-25 22:51:35 +05:00
Alex Ant f01de37a59 before make new document models 2026-01-25 13:40:56 +05:00
Alex Ant cee429a0a0 add udata model to a factory 2026-01-25 11:48:49 +05:00
Alex Ant 321ee89676 added all blagorost documents 2026-01-25 10:30:57 +05:00
Alex Ant aa60484315 make invest statement 2026-01-23 13:00:24 +05:00
Alex Ant b807df3ee8 document names refactoring & context component 2026-01-22 18:13:45 +05:00
Alex Ant c11e922573 registration with programs and agreements 2026-01-22 13:41:02 +05:00
Alex Ant 7135a3bbeb new documents 2026-01-21 21:49:35 +05:00
Alex Ant 142b87dd67 before make git 2026-01-20 21:23:02 +05:00
Alex Ant dff4579f28 project & component initialization & InitProjectStatement & InitProjectDecision 2026-01-19 17:39:20 +05:00
Alex Ant 2b3b662a9a generationAgreement Document & project initialization process 2026-01-19 14:24:05 +05:00
Alex Ant 98bc5195b1 blagorost decision tracking factory 2026-01-18 17:31:10 +05:00
Alex Ant a02912ccbb document updates 2026-01-17 11:47:48 +05:00
Alex Ant 2f1d29dfd2 Merge branch 'project-authorization-on-create' into dev 2026-01-16 22:02:48 +05:00
Alex Ant 11efacc4cb 1002 document generation agreement 2026-01-16 22:00:43 +05:00
Alex Ant 8133d0da3d register contributor with UHD 2026-01-16 12:34:47 +05:00
Alex Ant 093d63faae add zeus 2026-01-16 12:34:18 +05:00
Alex Ant 07f5e04488 authorization 2026-01-16 12:32:34 +05:00
Alex Ant acfc97fc7c permissions and boot fixs 2026-01-15 12:15:14 +05:00
Alex Ant 6e30554143 fix button 2026-01-13 18:25:54 +05:00
Alex Ant fa1c788c41 issue and project permissions & selectors 2026-01-13 18:01:59 +05:00
Alex Ant 3a688942c3 finalize_project and convert unused project funds to global program fund 2026-01-09 18:17:34 +05:00
Alex Ant 6797522618 blagorost masterplace 2026-01-07 17:11:47 +05:00
Alex Ant 4730a53313 requirements project -> component -> issue 2026-01-06 00:26:11 +05:00
Alex Ant 5a538792f0 project logs 2026-01-05 23:46:42 +05:00
Alex Ant 5f20289767 blagorost human project log 2026-01-04 23:43:54 +05:00
Alex Ant 4c7ed97a76 blagorost convert segment dialog 2026-01-04 21:43:23 +05:00
Alex Ant a9c2228e3c repair blagorost tests 2026-01-02 19:19:55 +05:00
Alex Ant ec44fcb7cb refactoring: user and certificates 2026-01-02 18:03:17 +05:00
Alex Ant 1f9c8d261b refactoring: wallet & user-certificate 2026-01-02 17:15:43 +05:00
Alex Ant 23ab3bd416 refactoring: system 2026-01-02 16:42:15 +05:00
Alex Ant 79482775d2 refactoring: settings 2026-01-02 10:40:27 +05:00
Alex Ant 2dcb3678b0 refactoring: payment-method 2026-01-02 10:28:48 +05:00
Alex Ant 8d7c206012 refactoring: notification 2026-01-02 10:03:37 +05:00
Alex Ant c21c264426 refactoring: meet interactor 2026-01-01 20:42:29 +05:00
Alex Ant 77a39c18f1 refactoring: make adapters for extensions 2026-01-01 20:11:25 +05:00
Alex Ant 65a00b0a8e refactoring: ledger 2026-01-01 19:11:56 +05:00
Alex Ant 0c2d5679f1 extensions reinit 2026-01-01 19:05:12 +05:00
Alex Ant 75d0e0de43 gateway refactoring 2026-01-01 18:49:59 +05:00
Alex Ant 19ff864eaa gateway refactoring 2026-01-01 14:30:37 +05:00
Alex Ant 6bbee7cb10 refactoring -> clean architecture 2026-01-01 12:57:37 +05:00
Alex Ant e268923cf6 down logger lever for powerup overdrawn balance 2025-12-31 13:14:30 +05:00
Alex Ant 4fb3d7182c chore(release): publish 2025-12-31 00:08:59 +05:00
Alex Ant 6e7a6ec032 chore(release): publish 2025-12-31 00:08:00 +05:00
Alex Ant 0e92c92f87 bug: повторное общее собрание не завершало онбординг кооператива 2025-12-30 21:37:37 +05:00
Alex Ant a6f1eb39ec chore(release): publish 2025-12-30 20:49:54 +05:00
Alex Ant 21364f6239 chore(release): publish 2025-12-30 18:24:48 +05:00
Alex Ant a0527094a9 fix a little 2025-12-30 18:24:17 +05:00
Alex Ant eda890c294 chore(release): publish 2025-12-30 17:59:11 +05:00
Alex Ant 1ed8db87cc openReplay http watcher 2025-12-30 17:57:57 +05:00
Alex Ant 136892478f chore(release): publish 2025-12-30 14:41:51 +05:00
Alex Ant aee90d31a0 chore(release): publish 2025-12-30 14:33:54 +05:00
Alex Ant 6fe632fda3 add repairdec action in soviet contract 2025-12-30 14:33:00 +05:00
Alex Ant fa975a2f5b auto cancel decisions full disable and postgres booter 2025-12-30 13:45:40 +05:00
Alex Ant bd5ab14d2f chore(release): publish 2025-12-28 20:44:51 +05:00
Alex Ant 32890bfda9 chore(release): publish 2025-12-28 15:10:11 +05:00
Alex Ant a3d4113b97 sentry backend integration 2025-12-28 15:09:13 +05:00
Alex Ant 8acfa722f8 chore(release): publish 2025-12-28 14:26:21 +05:00
Alex Ant 234beba06a sentry env 2025-12-28 14:24:55 +05:00
Alex Ant 90c27a0f73 chore(release): publish 2025-12-28 12:47:59 +05:00
Alex Ant 2577a5d2c2 remove logs 2025-12-28 12:47:25 +05:00
Alex Ant 84bf10b65b chore(release): publish 2025-12-28 12:15:59 +05:00
Alex Ant 5d70f5fd97 env refactoring rollback 2025-12-28 12:15:29 +05:00
Alex Ant f42cc59d53 chore(release): publish 2025-12-28 11:33:03 +05:00
Alex Ant d12b222d52 fix tracker assistant (disable it) 2025-12-28 11:32:22 +05:00
Alex Ant b663c7f9d4 env config refactoring 2025-12-28 11:24:26 +05:00
Alex Ant 30abfa7e23 chore(release): publish 2025-12-28 10:58:32 +05:00
Alex Ant 0be32c34c5 update 2025-12-28 10:58:09 +05:00
Alex Ant 8d4863b894 chore(release): publish 2025-12-28 10:43:19 +05:00
Alex Ant ad1ae8fb54 update openScreen assistant 2025-12-28 10:42:46 +05:00
Alex Ant b31e41bfd9 chore(release): publish 2025-12-27 20:49:02 +05:00
Alex Ant 999d5a937d SSR fix 2025-12-27 20:48:15 +05:00
Alex Ant 45ea543a4b chore(release): publish 2025-12-27 20:23:58 +05:00
Alex Ant 9d72a5e02d openScreen 2025-12-27 20:21:56 +05:00
Alex Ant 8973c45b4e chore(release): publish 2025-12-27 20:04:57 +05:00
Alex Ant b3e5a5dc62 complete refactoring for a clean architecture 2025-12-27 20:03:53 +05:00
Alex Ant d8bddadd42 chore(release): publish 2025-12-27 11:42:16 +05:00
Alex Ant aa552d1c80 refactoring #4 2025-12-27 11:41:23 +05:00
Alex Ant 6daac5f442 chore(release): publish 2025-12-26 23:53:27 +05:00
Alex Ant a8c453fbda refactoring #2 2025-12-26 23:52:43 +05:00
Alex Ant 3e15da5ad7 chore(release): publish 2025-12-26 19:46:46 +05:00
Alex Ant 8e776e7d42 chore(release): publish 2025-12-26 18:48:28 +05:00
Alex Ant de3d5654b4 mono monitor mongo -> psql migration & ipn model migration 2025-12-26 18:47:31 +05:00
Alex Ant b0e19ffa30 chore(release): publish 2025-12-26 17:22:25 +05:00
Alex Ant bacf451cf5 chore(release): publish 2025-12-26 16:58:44 +05:00
Alex Ant 2a5600b6af login bugfix 2025-12-26 16:58:13 +05:00
Alex Ant bfbc78d9b7 chore(release): publish 2025-12-26 13:41:36 +05:00
Alex Ant d509281bdc delete some migrations 2025-12-26 13:40:55 +05:00
Alex Ant 866fdfb4f6 chore(release): publish 2025-12-26 13:27:55 +05:00
Alex Ant 6c14d0f4c5 fix generator port 2025-12-26 13:27:23 +05:00
Alex Ant b31a8e3bf8 chore(release): publish 2025-12-26 12:46:11 +05:00
Alex Ant 7f3261e453 migrate tokens from mongo to postgres and clean arch 2025-12-26 12:45:09 +05:00
Alex Ant 861c3617dd payment providers refactoring 2025-12-26 10:51:57 +05:00
Alex Ant 1f4b1f5421 chore(release): publish 2025-12-26 10:04:34 +05:00
Alex Ant f851460a32 fix package 2025-12-26 10:03:09 +05:00
Alex Ant 992ac6d9eb chore(release): publish 2025-12-25 23:46:03 +05:00
Alex Ant 2e9ac57930 big service refactoring 2025-12-25 23:44:07 +05:00
Alex Ant ce8d090f27 chore(release): publish 2025-12-25 14:34:36 +05:00
Alex Ant 4ec8b59fd6 chore(release): publish 2025-12-25 14:32:42 +05:00
Alex Ant 6b086af8b4 upgrade chatwoot sdk 2025-12-25 14:30:57 +05:00
Alex Ant 52f95665ed chore(release): publish 2025-12-25 10:13:13 +05:00
Alex Ant d1ce5ab105 fix build chatwoot 2025-12-25 10:12:39 +05:00
Alex Ant 0fd10649f4 chore(release): publish 2025-12-25 00:24:37 +05:00
Alex Ant 3c65900768 support widget 2025-12-25 00:23:31 +05:00
Alex Ant 0b962b4fee board members refactoring 2025-12-24 17:06:18 +05:00
Alex Ant a58633fc5f chore(release): publish 2025-12-24 13:24:14 +05:00
Alex Ant 24c2ed3ae3 chore(release): publish 2025-12-23 23:22:46 +05:00
Alex Ant 84a77d98cf refactoring sendPOST and sendGET from desktop 2025-12-23 23:19:55 +05:00
Alex Ant 20e50e02e9 delete @coopenomics/controller package from desktop 2025-12-23 19:46:51 +05:00
Alex Ant c8bb354972 chore(release): publish 2025-12-22 18:47:11 +05:00
Alex Ant 3f9b73d211 chore(release): publish 2025-12-22 18:46:36 +05:00
Alex Ant 40bbffed17 bug fix 2025-12-22 18:46:11 +05:00
Alex Ant b16ec4e809 fix blagorost contract 2025-12-22 18:39:56 +05:00
Alex Ant 9629c895d5 chore(release): publish 2025-12-17 23:29:39 +05:00
Alex Ant f4420fcc03 doc update 2025-12-17 23:28:34 +05:00
Alex Ant 17f8c3e134 chore(release): publish 2025-12-17 22:20:38 +05:00
Alex Ant 02512a522c chore(release): publish 2025-12-17 21:47:10 +05:00
Alex Ant 4974f99842 blagorost off 2025-12-17 21:46:08 +05:00
Alex Ant a3d0c32be3 chore(release): publish 2025-12-17 21:33:01 +05:00
Alex Ant 31523160fc chore(release): publish 2025-12-17 21:25:53 +05:00
Alex Ant 183d5cdeec migration and little fix 2025-12-17 21:25:02 +05:00
Alex Ant 52fed810f2 chore(release): publish 2025-12-17 20:53:43 +05:00
Alex Ant f58d63da8d blagorost documents agenda proposals 2025-12-17 20:51:34 +05:00
Alex Ant 6793e6fbdc blagorost documents 2025-12-17 18:21:24 +05:00
Alex Ant 4f88e9b97d blagorost imgs, profile and other fixs 2025-12-17 09:35:32 +05:00
Alex Ant 5004cec9b3 chore(release): publish 2025-12-14 23:42:01 +05:00
Alex Ant 76c81e4209 chore(release): publish 2025-12-14 23:40:47 +05:00
Alex Ant 323043dc01 документация по общему собранию и т.п. 2025-12-14 23:39:41 +05:00
Alex Ant 37902ce70a chore(release): publish 2025-12-13 15:14:11 +05:00
Alex Ant c69e795d49 chore(release): publish 2025-12-13 15:12:28 +05:00
Alex Ant c3b82af95a 1c doc 2025-12-13 15:11:58 +05:00
Alex Ant 24510d4828 chore(release): publish 2025-12-13 13:45:35 +05:00
Alex Ant 11a04a99f7 1ccoop availability 2025-12-13 13:44:11 +05:00
Alex Ant 6e96eeaa05 chore(release): publish 2025-12-13 13:22:25 +05:00
Alex Ant 2c16d4af5a fix 2025-12-13 13:21:46 +05:00
Alex Ant d1f9cf43de chore(release): publish 2025-12-13 12:44:06 +05:00
Alex Ant 26fb11cb30 chore(release): publish 2025-12-13 12:21:45 +05:00
Alex Ant a7a3eb8658 weasyprint -> 67 2025-12-13 12:21:17 +05:00
Alex Ant fbedcd1f5f chore(release): publish 2025-12-13 11:28:37 +05:00
Alex Ant 6033af0f23 fix 2025-12-13 11:28:10 +05:00
Alex Ant 4809786b16 chore(release): publish 2025-12-13 11:19:11 +05:00
Alex Ant a37f40ff6e weasyprint #2 2025-12-13 11:18:25 +05:00
Alex Ant 44f5cc9de0 chore(release): publish 2025-12-13 10:51:12 +05:00
Alex Ant e059d0cbd9 Dockerfile 2025-12-13 10:50:25 +05:00
Alex Ant c51040b0de chore(release): publish 2025-12-13 10:42:39 +05:00
Alex Ant eba2abc108 downgrade weasyprint and upgrade base image 2025-12-13 10:41:46 +05:00
Alex Ant ed7626009a chore(release): publish 2025-12-13 10:11:33 +05:00
Alex Ant 442413ec6b up weasyprint version 2025-12-13 10:09:25 +05:00
Alex Ant 90986df641 onboarding 2025-12-13 09:31:42 +05:00
Alex Ant 8b505dbce3 cooperative onboarding process & chat with union 2025-12-11 20:47:16 +05:00
Alex Ant 2b26e9643b chore(release): publish 2025-12-10 15:31:43 +05:00
Alex Ant eb16f01839 docs and ledger refactoring 2025-12-10 13:50:59 +05:00
Alex Ant 872cf33d1c update 2025-12-02 18:39:54 +05:00
Alex Ant afbce19028 chore(release): publish 2025-12-02 18:13:18 +05:00
Alex Ant e27228e735 chore(release): publish 2025-12-02 18:09:56 +05:00
Alex Ant 3125232114 change CNAME in docs and fix publish CI 2025-12-02 18:09:07 +05:00
Alex Ant e552840cc4 chore(release): publish 2025-12-02 14:39:34 +05:00
Alex Ant 569142845a chore(release): publish 2025-12-02 14:37:38 +05:00
Alex Ant e62d837858 1c-integration and deploy bug fix 2025-12-02 14:35:58 +05:00
Alex Ant 27badfb88a chore(release): publish 2025-11-29 00:50:18 +05:00
Alex Ant e4d0781eb8 chore(release): publish 2025-11-29 00:44:02 +05:00
Alex Ant 93c8373335 disable setInterval on server side 2025-11-29 00:42:51 +05:00
Alex Ant 42bad6b4ea chore(release): publish 2025-11-28 13:08:14 +05:00
Alex Ant 83d4bd88cf chore(release): publish 2025-11-28 13:06:11 +05:00
Alex Ant 4141267104 disable unused routes 2025-11-28 13:05:04 +05:00
Alex Ant d5778f165b remove notifications on update 2025-11-28 12:16:54 +05:00
Alex Ant 7128e26a27 chore(release): publish 2025-11-28 12:15:17 +05:00
Alex Ant 78247e9969 bug fixes and logging improve 2025-11-28 12:14:13 +05:00
Alex Ant 66d36e034e chore(release): publish 2025-11-27 19:52:17 +05:00
Alex Ant 4100ee842c update 2025-11-27 19:49:59 +05:00
Alex Ant d4857c8e6e some fixes 2025-11-27 14:26:34 +05:00
Alex Ant 0f52781489 cmdK z-top & latest tag on docker production container 2025-11-26 17:27:08 +05:00
Alex Ant 332f19cd22 chore(release): publish 2025-11-26 13:13:59 +05:00
Alex Ant 53a1c103d6 chore(release): publish 2025-11-26 12:55:34 +05:00
Alex Ant addf7a3e6b fix 2025-11-26 12:54:19 +05:00
Alex Ant c76078ea06 chore(release): publish 2025-11-26 12:51:24 +05:00
Alex Ant 9299288e8a bug fix: chat loading and console.logs for debug router problem 2025-11-26 12:49:42 +05:00
Alex Ant dc34f24ee2 chore(release): publish 2025-11-26 11:23:40 +05:00
Alex Ant fe83bf1483 fix latest tag on testnet 2025-11-26 11:22:41 +05:00
Alex Ant c184f9281d chore(release): publish 2025-11-26 00:14:11 +05:00
Alex Ant 3127a69b67 chore(release): publish 2025-11-26 00:10:29 +05:00
Alex Ant d7326c4f82 chore(release): publish 2025-11-25 16:12:22 +05:00
Alex Ant f8478284b6 backward capability 2025-11-25 16:11:26 +05:00
Alex Ant 1c910de4b1 chore(release): publish 2025-11-25 10:56:15 +05:00
Alex Ant 2c3cb955ef fix 2025-11-25 10:55:36 +05:00
Alex Ant 1d7746d839 chore(release): publish 2025-11-25 10:10:36 +05:00
Alex Ant e16d2ba238 chore(release): publish 2025-11-24 22:26:05 +05:00
Alex Ant 60f8b448ec coopgram -> chatcoop & mobile client instruction 2025-11-24 22:24:33 +05:00
Alex Ant c0d61f29a8 empty settings fix & matrix room creation fix 2025-11-24 20:10:57 +05:00
Alex Ant c47b99f9ee chore(release): publish 2025-11-24 19:02:09 +05:00
Alex Ant 653429a6d6 docs generation fix & docker compose env missing params fix 2025-11-24 19:01:23 +05:00
Alex Ant c2250e1817 chore(release): publish 2025-11-24 17:35:56 +05:00
Alex Ant 92ca48d65f make common group room & fix deploy workflow 2025-11-24 17:33:17 +05:00
Alex Ant 2f53d9a79d chatcoop prerelease 2025-11-24 11:44:59 +05:00
Alex Ant d025bfe2da Merge branch 'element' into dev 2025-11-22 15:28:41 +05:00
Alex Ant fbc2460ac4 typeorm fix expiration and add complete & fail date 2025-11-22 15:23:49 +05:00
Alex Ant 76c2800275 extensions migration system, extensions logs, powerup log 2025-11-22 10:59:08 +05:00
Alex Ant 536bf984ee powerup page 2025-11-21 19:33:09 +05:00
Alex Ant 23f8af43ee chore(release): publish 2025-11-20 20:26:39 +05:00
Alex Ant eba54bf2e7 fix amount precision in document 2025-11-20 20:25:29 +05:00
Alex Ant 50270e6541 rub to axon convertation 2025-11-20 20:18:36 +05:00
Alex Ant 5f7d9e80ee chore(release): publish 2025-11-20 12:56:57 +05:00
Alex Ant a71ef35d5c delegate fees fund and convert_to_axon action 2025-11-20 12:55:59 +05:00
Alex Ant 2cf5291831 chore(release): publish 2025-11-19 19:40:44 +05:00
Alex Ant 75e3e9dd7b fix convertation system 2025-11-19 19:40:08 +05:00
Alex Ant 7a75365d2f chore(release): publish 2025-11-19 15:38:27 +05:00
Alex Ant 7a23d59aa1 injection AXON to any coop 2025-11-19 15:37:20 +05:00
Alex Ant 2583423600 chore(release): publish 2025-11-19 12:28:35 +05:00
Alex Ant 1d748a0424 generate and process AXON - GOVERN convertation 2025-11-19 12:26:05 +05:00
Alex Ant 86172790d1 chore(release): publish 2025-11-18 11:51:59 +05:00
Alex Ant 92c9103059 currentUser -> session stores refactoring 2025-11-18 11:50:07 +05:00
Alex Ant 16393dbc9d chore(release): publish 2025-11-17 22:10:07 +05:00
Alex Ant e841b0ef03 fix login bug 2025-11-17 22:09:06 +05:00
Alex Ant 27c7ae9d76 chore(release): publish 2025-11-17 14:04:59 +05:00
Alex Ant dc3a40675d fix health check 2025-11-17 14:04:07 +05:00
Alex Ant 31e65ac2e3 chore(release): publish 2025-11-17 13:32:08 +05:00
Alex Ant c2444d1b09 health-check route 2025-11-17 13:31:37 +05:00
Alex Ant 2faadae4cf chore(release): publish 2025-11-17 12:29:25 +05:00
Alex Ant d24e51c355 some fixes 2025-11-17 12:28:37 +05:00
Alex Ant 8ed8af1b9c chore(release): publish 2025-11-16 14:10:06 +05:00
Alex Ant 5f6b416f26 installer fix, parser init fix, service worker fix 2025-11-16 14:06:43 +05:00
Alex Ant 3671c05573 chore(release): publish 2025-11-15 18:53:03 +05:00
Alex Ant db6eed9292 pre-release 2025-11-15 18:51:37 +05:00
Alex Ant 4c903ba0bb chore(release): publish 2025-11-14 12:26:30 +05:00
Alex Ant 9eee216065 fix parser initializator 2025-11-14 12:25:58 +05:00
Alex Ant 9e1dd02d70 chore(release): publish 2025-11-14 11:58:32 +05:00
Alex Ant b986bf9bcc update 2025-11-14 11:56:51 +05:00
Alex Ant a3e0e62efc chore(release): publish 2025-11-14 11:25:42 +05:00
Alex Ant 8646c5acf6 boolean factory fix 2025-11-14 11:24:49 +05:00
Alex Ant dab9465755 chore(release): publish 2025-11-13 20:32:34 +05:00
Alex Ant 3a076cc4ea fix parser 2025-11-13 20:31:38 +05:00
Alex Ant 1b6d1ea0ef chore(release): publish 2025-11-13 20:19:25 +05:00
Alex Ant c490284c65 initializator for parser 2025-11-13 20:17:19 +05:00
Alex Ant c3ca329138 installation step 2025-11-13 18:33:43 +05:00
Alex Ant d0f73c32bb chore(release): publish 2025-11-13 11:18:18 +05:00
Alex Ant 79e0da7cf2 fix user notifications 2025-11-13 11:16:22 +05:00
Alex Ant b261f505aa chore(release): publish 2025-11-12 18:06:40 +05:00
Alex Ant 65c4c95cbe connection page and regcoop payer 2025-11-12 18:05:34 +05:00
Alex Ant 5b3c9c9055 chore(release): publish 2025-11-11 19:12:42 +05:00
Alex Ant d32d4f845c coop connect page 2025-11-11 19:11:25 +05:00
Alex Ant 637950d37f chore(release): publish 2025-11-10 21:01:05 +05:00
Alex Ant 0e1ede58e5 some installation process fixs and regcoop modify instead of emplace when exists 2025-11-10 20:59:36 +05:00
Alex Ant e914a11768 chore(release): publish 2025-11-10 12:47:47 +05:00
Alex Ant 73d66dab35 command+k menu 2025-11-10 12:46:45 +05:00
Alex Ant 634766a08e chore(release): publish 2025-11-10 09:47:19 +05:00
Alex Ant 5fbc450e96 ConnectionStepper 2025-11-10 09:45:11 +05:00
Alex Ant 5acd7ae2c4 chore(release): publish 2025-11-09 20:48:49 +05:00
Alex Ant 09578ddc5d provider integration 2025-11-09 20:47:16 +05:00
Alex Ant 8270801711 chore(release): publish 2025-11-09 16:26:20 +05:00
Alex Ant de91c3cfc8 sdk public constructor 2025-11-09 16:22:43 +05:00
Alex Ant 06888a2061 chore(release): publish 2025-11-08 20:58:10 +05:00
Alex Ant cde2d33d03 chore(release): publish 2025-11-08 20:56:36 +05:00
Alex Ant 9cf89f95d1 fix 2025-11-08 20:55:28 +05:00
Alex Ant 20486e15ea chore(release): publish 2025-11-08 14:18:32 +05:00
Alex Ant 420c403da1 chore(release): publish 2025-11-08 14:14:44 +05:00
Alex Ant cb8fdf3461 startup notification 2025-11-08 14:14:04 +05:00
Alex Ant 0937d08770 chore(release): publish 2025-11-08 13:59:05 +05:00
Alex Ant 9b1fd8e1aa chore(release): publish 2025-11-08 13:58:14 +05:00
Alex Ant d87861142c chore(release): publish 2025-11-08 12:47:15 +05:00
Alex Ant ff5fc1d0f3 update publish scripts 2025-11-08 12:46:45 +05:00
Alex Ant d5a671cbb8 update config 2025-11-08 12:42:51 +05:00
Alex Ant d0508cbd96 chore(release): publish 2025-11-08 11:58:39 +05:00
Alex Ant 12098cf8ac server provisioned notification workflow 2025-11-08 11:48:35 +05:00
Alex Ant 2557c35bea add dev mode to smart-contracts, make notifications external accessable, make boot works 2025-11-07 20:20:17 +05:00
Alex Ant 11f23bbd77 chore(release): publish 2025-11-07 12:25:13 +05:00
Alex Ant 2b2ec729ac external notification resolver 2025-11-07 12:24:18 +05:00
Alex Ant 9292acec8c chore(release): publish 2025-11-06 21:49:46 +05:00
Alex Ant 3095ed5375 installation process 2025-11-06 20:06:40 +05:00
Alex Ant a333e303c1 improve installation process, make privacy policy public and acceptable 2025-11-05 22:13:10 +05:00
Alex Ant bd8512feab clear install 2025-11-03 19:16:57 +05:00
Alex Ant c235fc4a7a fix save wif 2025-11-03 15:55:55 +05:00
Alex Ant 9c283b9aee invite page & set soviet refactoring 2025-11-03 14:16:37 +05:00
Alex Ant 4e824d739b all notifications going throw novu now 2025-11-03 11:09:34 +05:00
Alex Ant fcbbc792b0 make installation starts 2025-11-02 21:58:44 +05:00
Alex Ant ba7cf8e79e Merge branch 'installation' into refactoring 2025-11-02 09:48:41 +05:00
Alex Ant 4ab49d8e43 delete application, domain and infra module aggregators 2025-11-02 09:45:19 +05:00
Alex Ant 7f864db80d wtf 2025-11-01 21:39:23 +05:00
Alex Ant 772a163693 parser fix 2025-11-01 18:04:11 +05:00
Alex Ant c8e106f272 update 2025-11-01 17:53:16 +05:00
Alex Ant ade4f0a1d4 ssr bug fix 2025-11-01 17:14:23 +05:00
Alex Ant 4fcf933dd1 fix: no SSR for some modules 2025-11-01 14:03:45 +05:00
Alex Ant 1fb60771ca fix: synchronize: true in typeorm.module.ts 2025-10-31 23:32:31 +05:00
Alex Ant 2cd391e106 hide capital app for now 2025-10-31 19:52:24 +05:00
Alex Ant 196f3bcba1 level & energy system 2025-10-27 21:36:02 +05:00
Alex Ant bc73c5ca86 contract gamification 2025-10-27 16:19:56 +05:00
Alex Ant f4badc15d1 редактирование участника, шаблон "о себе" 2025-10-27 12:50:51 +05:00
Alex Ant 76f731d0cd poll requests for update content 2025-10-26 18:27:08 +05:00
Alex Ant 5e22858ab4 some bugs and permissions 2025-10-26 15:45:15 +05:00
Alex Ant bc1c54c43e notifications on novu improve (sanity), make a coop settings for chairman and select default workspace / page 2025-10-25 20:19:10 +05:00
Alex Ant 95ac0d36f8 a lot of changes 2025-10-22 19:53:40 +05:00
Alex Ant 2bee3eb179 unique participants count and workflow notification 2025-10-21 17:13:20 +05:00
Alex Ant 52165f2a0b microWallet & workspaceMenu rework 2025-10-20 21:12:53 +05:00
Alex Ant 9f2da226f4 extensionsStore refactoring and make it with multi-desktops 2025-10-20 17:26:24 +05:00
Alex Ant 46b999317d result submission 2025-10-20 15:35:32 +05:00
Alex Ant 80bce3c9c2 refactoring, optimization and improvement 2025-10-17 19:33:07 +05:00
Alex Ant 90b25b4bd8 fab | visual refactoring 2025-10-16 20:34:56 +05:00
Alex Ant f562f1eafd Merge branch 'dev' into capital 2025-10-16 10:27:23 +05:00
Alex Ant ff520622ff chore(release): publish 2025-10-16 10:25:26 +05:00
Alex Ant 1a6c6a4f31 fix parser 2025-10-16 01:32:23 +05:00
Alex Ant 4a9e0388f4 fix parser start block 2025-10-16 01:30:55 +05:00
Alex Ant e47b2a971e chore(release): publish 2025-10-15 23:12:28 +05:00
Alex Ant 96777ec095 delete mongo transactions 2025-10-15 23:00:23 +05:00
Alex Ant 52019deef5 ComponentPage 2025-10-15 22:51:30 +05:00
Alex Ant c26a534ff6 secondary route menu 2025-10-15 20:36:24 +05:00
Alex Ant e5be5c0b05 syncers refactoring and frontend 2025-10-15 13:49:20 +05:00
Alex Ant 5b07f52641 hard update 2025-10-14 22:06:23 +05:00
Alex Ant e0109cb530 pushResult подготовка и отправка документов с ожиданием решения совета 2025-10-12 19:41:53 +05:00
Alex Ant 1496dd1598 approvals with auth start 2025-10-07 19:41:54 +05:00
Alex Ant efcaeb2f00 set plan and other | going to voting 2025-10-07 11:31:56 +05:00
Alex Ant 1252946fe5 permissions and booter 2025-10-05 10:55:53 +05:00
Alex Ant 2913d5f636 some widgets and filters 2025-10-02 17:35:06 +05:00
Alex Ant c50beb3d43 some updates 2025-09-29 13:34:52 +05:00
Alex Ant 46b559001a some refactoring 2025-09-28 16:38:19 +05:00
Alex Ant 55a2e2e060 agreement repo and mutation 2025-09-28 15:48:56 +05:00
Alex Ant 12364a052f desktop agremeent features 2025-09-28 13:18:38 +05:00
Alex Ant 45ac971035 entity log 2025-09-28 11:19:50 +05:00
Alex Ant 26b818c9a6 update 2025-09-27 17:58:04 +05:00
Alex Ant 007836f52e contributor registration #1 2025-09-25 20:16:58 +05:00
Alex Ant ed0982770b mutations for all document generations 2025-09-25 12:47:17 +05:00
Alex Ant dcc72e90b7 factory capital documents basic templates 2025-09-24 21:52:34 +05:00
Alex Ant b428660944 project voting skeleton 2025-09-23 12:56:22 +05:00
Alex Ant 0008dcc0ee time tracker #3 2025-09-22 22:56:45 +05:00
Alex Ant e3fbf3981d time tracker personal time limit 2025-09-22 17:04:09 +05:00
Alex Ant c5e9244a08 selector fix 2025-09-21 23:55:11 +05:00
Alex Ant e1fd823c13 time tracker 2025-09-21 23:53:21 +05:00
Alex Ant 346f0d636c time tracker sdk queries 2025-09-21 20:42:28 +05:00
Alex Ant 315a259e5b lang refactoring 2025-09-21 16:09:19 +05:00
Alex Ant 3157a03c74 time tracking service prototype 2025-09-21 14:50:18 +05:00
Alex Ant 045807a748 edit project and create commit simple button on tasks 2025-09-20 20:52:53 +05:00
Alex Ant ea0e12ac80 update 2025-09-20 17:33:07 +05:00
Alex Ant 692060af6c update 2025-09-19 20:42:16 +05:00
Alex Ant d8b23a4b5c issues create 2025-09-19 10:41:29 +05:00
Alex Ant 074bf55d6c stories complete 2025-09-18 16:28:51 +05:00
Alex Ant 84e505b817 before make pain 2025-09-17 21:23:52 +05:00
Alex Ant a12e6ff603 taskPage 2025-09-17 16:40:18 +05:00
Alex Ant b01d662a1c components 2025-09-16 23:28:34 +05:00
Alex Ant e631dad499 getState, fix some bugs 2025-09-16 17:28:01 +05:00
Alex Ant 7ab0bfdd6b optional right drawer 2025-09-15 22:52:17 +05:00
Alex Ant 35a4db43fb add all entities and make extension store better 2025-09-13 01:02:21 +05:00
Alex Ant 094028006b make new queries and selectors 2025-09-11 22:21:53 +05:00
Alex Ant c12f42fcac some selectors, queries, features and entities 2025-09-11 19:10:37 +05:00
Alex Ant 3e498b098b refactoring #2 2025-09-11 13:03:21 +05:00
Alex Ant bbf1a1a544 refactoring 2025-09-11 12:15:05 +05:00
Alex Ant 42d57f30bf update names 2025-09-10 19:28:13 +05:00
Alex Ant 19967a9ad0 update 2025-09-10 15:23:33 +05:00
Alex Ant 9d1a8f12d8 main domain model 2025-09-10 14:22:14 +05:00
Alex Ant 57bebebe09 domain entities synced with blockchain 2025-09-08 13:47:40 +05:00
Alex Ant d19303cd62 typeorm repositories 2025-09-07 21:06:54 +05:00
Alex Ant 7c96e46a37 domain entities and infrastructure mappers 2025-09-07 20:44:28 +05:00
Alex Ant f75e68f8ce before refactoring 2025-09-06 16:42:29 +05:00
Alex Ant 9b922b00c1 coopgram base plugin 2025-09-06 01:17:31 +05:00
Alex Ant c8d9ee2457 migration fixs 2025-09-05 23:22:49 +05:00
Alex Ant a29f23086a update migrations 2025-09-05 23:07:27 +05:00
Alex Ant 4a76365df4 migrator fix 2025-09-05 22:56:08 +05:00
Alex Ant 972264844a migrator commands and subcommands 2025-09-05 22:46:39 +05:00
Alex Ant e23e6f3c1a some domain modules for capital 2025-09-05 15:03:48 +05:00
Alex Ant 03c10382d1 save deltas and actions and forks to main repositories 2025-09-04 14:21:20 +05:00
Alex Ant 3abe24aa18 refactoring, double bus refactoring, delete notificator module, desktop fix 2025-09-03 22:30:05 +05:00
Alex Ant 2a4eabcda5 update 2025-09-02 11:36:59 +05:00
Alex Ant 280d98c9c4 update docs 2025-09-02 11:35:46 +05:00
Alex Ant 227c5c80c8 chore(release): publish 2025-09-01 20:20:41 +05:00
Alex Ant edd00a6ab5 add capital to whitelist 2025-09-01 19:29:11 +05:00
Alex Ant d57bb17fc7 fix package.json 2025-09-01 19:00:32 +05:00
Alex Ant 098da5c868 small refactoring 2025-09-01 16:41:26 +05:00
Alex Ant dfc17bcc26 complete common tests 2025-09-01 14:18:54 +05:00
Alex Ant 7a5eab104e common capital tests 2025-09-01 11:37:54 +05:00
Alex Ant e0bf815377 cut some in docs 2025-08-27 22:48:37 +05:00
Alex Ant 2cbc6f2890 update 2025-08-27 22:46:38 +05:00
Alex Ant 5859b2c08b some fixs 2025-08-27 22:11:04 +05:00
Alex Ant 44eaa9dc8b economic fix 2025-08-27 22:03:06 +05:00
Alex Ant 49cd7a41dd documentation updates and some capital bug fix 2025-08-27 21:25:27 +05:00
Alex Ant 53de5ece21 test repair 2025-08-27 16:03:00 +05:00
Alex Ant 90dffa5fcc workflow 2025-08-27 00:19:13 +05:00
Alex Ant ac6cd0ca15 update 2025-08-27 00:05:24 +05:00
Alex Ant 0e970128ab update 2025-08-27 00:03:00 +05:00
Alex Ant 9fc373384d update 2025-08-26 23:23:28 +05:00
Alex Ant a76bd2ea55 fix header 2025-08-26 23:15:59 +05:00
Alex Ant 3c610b74d2 update package.json 2025-08-26 20:07:39 +05:00
Alex Ant 0623005ff4 effects, documents and processes 2025-08-26 19:58:20 +05:00
Alex Ant 8b032eba9a some docs 2025-08-25 20:11:42 +05:00
Alex Ant e3229b85fd before update 2025-08-24 11:40:24 +05:00
Alex Ant 1178431b8f update docx 2025-08-22 23:44:35 +05:00
Alex Ant 9d92c4a2b1 update docs 2025-08-22 17:54:10 +05:00
Alex Ant 0bda8707ce before delete anchors 2025-08-22 12:35:16 +05:00
Alex Ant 9cb7d3a0fd docs 2025-08-21 17:01:13 +05:00
Alex Ant f1204f948a update docx 2025-08-20 21:54:54 +05:00
Alex Ant 455b8dafb0 start make doc 2025-08-20 21:53:24 +05:00
Alex Ant fe5a32d95b some tests 2025-08-19 20:19:06 +05:00
Alex Ant b34f6f1690 direct coordinator rewards 2025-08-12 15:18:06 +05:00
Alex Ant a89bc35c6f before coordinators distribution change 2025-08-12 11:51:20 +05:00
Alex Ant e551b6c202 restore losted actions in fund contract 2025-08-08 20:27:09 +05:00
Alex Ant c6ed1afc51 test prepare 2025-08-08 20:24:20 +05:00
Alex Ant 4bedebb74d capital -> cooptypes 2025-08-08 19:38:25 +05:00
Alex Ant 741fc7eb05 готово к отладке 2025-08-08 16:51:46 +05:00
Alex Ant 000da1197c voting by vodyanov system 2025-08-03 16:45:11 +05:00
Alex Ant dd8be29d54 core / startproject 2025-08-01 17:51:15 +05:00
Alex Ant 099c2c7ff4 capital прием инвестиций и расчеты 2025-07-31 21:14:21 +05:00
Alex Ant 874232a152 Merge branch 'dev' into capital 2025-07-30 13:18:14 +05:00
Alex Ant d21f046e1f ignore DS_store 2025-07-30 13:17:58 +05:00
Alex Ant ef0e25878e Merge branch 'dev' into capital 2025-07-30 13:17:35 +05:00
Alex Ant cd37619af1 ledger - переход на debet и credit транзакции 2025-07-30 13:15:58 +05:00
Alex Ant 209ee18943 capital refactoring 2025-07-30 10:15:21 +05:00
Alex Ant aff7733a5b refactoring capital contract 2025-07-29 13:20:42 +05:00
Alex Ant 4bb65921e4 Merge branch 'dev' into capital 2025-07-29 10:02:03 +05:00
Alex Ant 26216a6a8c списание и отмена списания в истории 2025-07-29 10:01:28 +05:00
Alex Ant 60c3f11d7e fix 2025-07-29 00:40:24 +05:00
Alex Ant fcab08bfab история движений средств по счетам 2025-07-29 00:17:33 +05:00
Alex Ant e69ba466e1 chore(release): publish 2025-07-28 21:08:02 +05:00
Alex Ant 675e85ee09 fix precision 2025-07-28 20:26:31 +05:00
Alex Ant 36ec13b2c4 Merge branch 'ledger' into dev 2025-07-28 18:14:06 +05:00
Alex Ant 0b9c36e3ce Merge branch 'dev' into capital 2025-07-28 17:31:25 +05:00
Alex Ant 07cf895447 migration msg change 2025-07-28 17:30:10 +05:00
Alex Ant 028f21f0cf complete ledger contract 2025-07-28 17:14:06 +05:00
Alex Ant 77724e363d замена контракта fund на ledger 2025-07-27 13:13:58 +05:00
Alex Ant 15863d8a5a appendix еще не работает 2025-07-27 10:02:35 +05:00
Alex Ant b836af58f0 Merge branch 'dev' of github.com:coopenomics/mono into capital 2025-07-26 19:02:15 +05:00
Alex Ant ef5d880f14 chore(release): publish 2025-07-23 21:09:51 +05:00
Alex Ant 15fd03b4c0 устранена проверка времени подписи на голосовании 2025-07-23 21:09:07 +05:00
Alex Ant cac06f3e17 chore(release): publish 2025-07-23 15:13:43 +05:00
Alex Ant 6d81c62cdf setWif for cooperative 2025-07-23 15:12:30 +05:00
Alex Ant 60e319589d chore(release): publish 2025-07-20 21:35:08 +05:00
Alex Ant 7723a5785d Merge branch 'testnet' 2025-07-20 21:34:49 +05:00
Alex Ant dd982fe6e2 Merge branch 'dev' into testnet 2025-07-20 21:30:12 +05:00
Alex Ant c02dfeaa97 bug fix на составном префиксе кооператива при голосовании на общем собрании 2025-07-20 21:29:00 +05:00
Alex Ant a3d513afb0 update gitignore 2025-07-20 12:08:36 +05:00
Alex Ant 40fa99a1f9 смарт-контракт адаптирован к ТЗ, рыба контроллера 2025-07-20 12:06:46 +05:00
Alex Ant f26c996095 chore(release): publish 2025-07-15 17:17:20 +05:00
Alex Ant 012c4dfb9f fix 2025-07-15 17:15:14 +05:00
Alex Ant 9337ca2616 chore(release): publish 2025-07-15 16:59:47 +05:00
Alex Ant 5dcec4bcfd Merge branch 'testnet' 2025-07-15 16:57:48 +05:00
Alex Ant ed2e5e4d09 fix build image 2025-07-15 10:37:42 +05:00
Alex Ant 2249f52c32 fix build 2025-07-15 10:19:45 +05:00
Alex Ant f4ef5d2b53 notifications release 2025-07-15 09:59:21 +05:00
Alex Ant a92c5d6ce0 pwa configuration fix and novu subscribers fix 2025-07-14 13:38:34 +05:00
Alex Ant b61ceaead6 widget mode 2025-07-10 19:47:11 +05:00
Alex Ant 0672cfc8f3 delete notificator2 2025-07-10 17:29:43 +05:00
Alex Ant b5859a43cc Merge branch 'dev' into testnet 2025-07-10 16:49:33 +05:00
Alex Ant de1cd7c737 pwa push notifications 2 2025-07-10 16:45:07 +05:00
Alex Ant f588312ad3 pwa push notifications 2025-07-10 16:44:42 +05:00
Alex Ant 643ef1fa45 chore(release): publish 2025-07-08 14:17:04 +05:00
Alex Ant ec38a4ed33 reset and invite emails fix 2025-07-08 14:15:07 +05:00
Alex Ant defbd80ce0 fix contacts 2025-07-08 13:08:42 +05:00
Alex Ant f11b91e7fa auto reload on update 2025-07-08 12:56:05 +05:00
Alex Ant 58bb4d5a7f fix contacts bug 2025-07-08 12:43:01 +05:00
Alex Ant d92af60d9b лист подключенных кооперативов и документация 2025-07-08 10:14:04 +05:00
Alex Ant bca1e043bd chore(release): publish 2025-07-07 10:26:39 +05:00
Alex Ant 7719175e85 update 2025-07-07 10:13:31 +05:00
Alex Ant 046146c4d8 delete sdk docs from repo 2025-07-07 09:45:43 +05:00
Alex Ant 0e2f66b35a add gitignore 2025-07-07 09:45:06 +05:00
Alex Ant 56b9ff1dc9 docs, registration fix and connection button fix 2025-07-07 09:44:06 +05:00
Alex Ant dab8e78cd5 chore(release): publish 2025-07-06 23:15:03 +05:00
Alex Ant 67dd27b9a1 pwa rollback 2025-07-06 23:11:29 +05:00
Alex Ant 4605985a47 fix 2025-07-06 22:45:39 +05:00
Alex Ant 02ac27342a fix exlude error 2025-07-06 22:37:06 +05:00
Alex Ant cbc59a4a1c chore(release): publish 2025-07-06 21:48:06 +05:00
Alex Ant 02758d96c7 PWA service worker update 2025-07-06 21:44:36 +05:00
Alex Ant 12752134fd стол председателя 2025-07-06 17:32:43 +05:00
Alex Ant 504e70441b move exit button 2025-07-06 14:34:58 +05:00
Alex Ant 85cd16e793 navigation guard fix & desktop store left drawer mobile improve 2025-07-06 13:22:15 +05:00
Alex Ant aa2277f05e visual fixs 2025-07-06 11:46:21 +05:00
Alex Ant 27eb96722a chore(release): publish 2025-07-05 18:14:55 +05:00
Alex Ant 0215096c9e изменение принципа отображения кнопок действия 2025-07-05 18:13:31 +05:00
Alex Ant 90d8c51402 фикс гоночного бага при входе, демонстрация входящих оповещений всплывками 2025-07-05 16:45:51 +05:00
Alex Ant ba0bbfefe7 fix boot index 2025-07-05 13:02:25 +05:00
Alex Ant dd65673c1e pwa+ssr configuration 2025-07-05 12:54:30 +05:00
Alex Ant 2f3f8de682 fix 2025-07-05 10:18:32 +05:00
Alex Ant 3ce6fcad3a fix 2025-07-05 09:43:43 +05:00
Alex Ant 4302e7426e update quasar config 2025-07-04 23:09:25 +05:00
Alex Ant 4e246c35c8 try it 2025-07-04 22:44:43 +05:00
Alex Ant 0cbcae9624 update 2025-07-04 21:35:32 +05:00
Alex Ant 313aed606f update 2025-07-04 21:24:47 +05:00
Alex Ant aade735c79 Merge branch 'dev' into testnet 2025-07-04 21:17:50 +05:00
Alex Ant 1e5786a142 looking for bug 2025-07-04 21:14:45 +05:00
Alex Ant 3e5e5eeafa Merge branch 'dev' into testnet 2025-07-04 21:07:56 +05:00
Alex Ant 8a48ee8e14 logging 2025-07-04 21:04:56 +05:00
Alex Ant 6a89981c77 try add env to PWA 2025-07-04 19:59:55 +05:00
Alex Ant 03c014fdda rollback 2025-07-04 19:32:30 +05:00
Alex Ant ae683cd3c9 rollback env 2025-07-04 19:03:26 +05:00
Alex Ant a0dcae0882 pwa env inject 2025-07-04 18:34:43 +05:00
Alex Ant 6e839b210c update 2025-07-04 17:06:08 +05:00
Alex Ant c7f4f62e93 update package.json 2025-07-04 16:50:59 +05:00
Alex Ant 214aba8f01 pwa 2025-07-04 16:07:38 +05:00
Alex Ant 153c9d944f Merge branch 'notifications' into dev 2025-07-04 13:48:05 +05:00
Alex Ant 99a9d15871 pwa implementation 2025-07-04 13:47:42 +05:00
Alex Ant f6fb905ef8 Генерация, синхронизация и выдача данных для центра уведомлений 2025-07-04 13:12:33 +05:00
Alex Ant a5456452f6 http auth 2025-07-03 18:48:50 +05:00
Alex Ant 48cd9af739 Merge commit 'b9ae66e557f82e1265ae8d71c7fd6ec38509b5f1' into notifications 2025-07-03 18:09:23 +05:00
Alex Ant 01fac428d5 chore(release): publish 2025-07-03 18:05:11 +05:00
Alex Ant 3acce100f6 Merge branch 'testnet' 2025-07-03 18:04:50 +05:00
Alex Ant ba2dfe6598 Merge branch 'dev' into testnet 2025-07-03 18:04:27 +05:00
Alex Ant 46600c38a8 fast bug fix 2025-07-03 18:04:17 +05:00
Alex Ant b9ae66e557 чуть не забыл 2025-07-03 18:03:31 +05:00
Alex Ant bed9010918 some steps 2025-07-03 17:58:45 +05:00
Alex Ant d13ccbde71 bug: meet service improve 2025-07-02 13:27:31 +05:00
Alex Ant 2e2aac0413 chore(release): publish 2025-07-02 12:16:36 +05:00
Alex Ant 5f18cff344 fix: meet сервис на отправку уведомления о повторном собрании 2025-07-02 11:58:51 +05:00
Alex Ant 830300ea81 chore(release): publish 2025-07-01 21:03:01 +05:00
Alex Ant 9da2fcfbca migration 2025-07-01 20:31:21 +05:00
Alex Ant ece68df495 добавлены анимации для входа и выхода меню, улучшена логика рендеринга. Обновлены стили и добавлен ключ для перерендера при смене маршрутов. Исправлены мелкие недочеты в других компонентах. 2025-07-01 16:46:33 +05:00
Alex Ant 6a43ddbee9 chore(release): publish 2025-07-01 16:04:01 +05:00
Alex Ant ee58596ed0 Упрощен компонент ShadowHtml: удалена проверка на клиентскую среду, добавлены логи для отладки, обновлено состояние миграции с изменением тестового файла. 2025-07-01 15:45:10 +05:00
Alex Ant 5bce6e77ae Исправлено название типа платежа "Возврат средств" на "Возврат взноса" в PaymentDomainEntity. 2025-07-01 13:36:13 +05:00
Alex Ant 5dec45c0c8 Рефакторинг пользователя в сессии на фронте, правки визуального отображения всех страниц, управление исходящими платежами в шлюзе, возврат паевого взноса в кошельке. 2025-07-01 13:34:46 +05:00
Alex Ant b7ba6500e4 Новая архитектура для входящих и исходящих платежей 2025-06-26 20:20:58 +05:00
Alex Ant 2a263d749b returnByMoneyDecision Document 2025-06-25 20:34:12 +05:00
Alex Ant 3a21af48d1 Добавляем шаблон заявления на возврат паевого взноса с ЦК 2025-06-24 16:18:34 +05:00
Alex Ant cb3bfe99ce chore(release): publish 2025-06-24 09:07:26 +05:00
Alex Ant 328d51622f fix navigation guard bug 2025-06-24 08:50:05 +05:00
Alex Ant 38ead74697 поле ввода для поиска пайщика и извлечения его username 2025-06-23 20:56:07 +05:00
Alex Ant ffd4d72850 search by private account 2025-06-23 13:30:34 +05:00
Alex Ant d23d90a794 Корректное удаление кооперативного участка. Общее собранее уполномоченных. Правки title шаблонов. 2025-06-19 12:09:10 +05:00
Alex Ant c74036ad26 chore(release): publish 2025-06-19 10:00:51 +05:00
Alex Ant a146a9f424 Правка сообщений с ошибками на фронте, расширение шаблонов общих собраний на повторяемость. 2025-06-19 09:41:41 +05:00
Alex Ant ddc0c82cee chore(release): publish 2025-06-14 21:27:59 +05:00
Alex Ant bab09ac0d7 FATALITY BUG FIX 2025-06-14 21:26:41 +05:00
Alex Ant 8a6eb912c5 Revert "откатываем функционал"
This reverts commit e5642cd752.
2025-06-14 20:28:02 +05:00
Alex Ant b5fbd40ea3 update workflow #2 2025-06-14 17:56:14 +05:00
Alex Ant 46b1c085cd workflow fix 2025-06-14 16:09:22 +05:00
Alex Ant e5642cd752 откатываем функционал 2025-06-14 13:40:01 +05:00
Alex Ant be933e9085 fix hash router 2025-06-14 11:07:35 +05:00
Alex Ant 26769675c7 rollback 2025-06-14 09:07:57 +05:00
Alex Ant 672d6d67aa chore(release): publish 2025-06-13 20:45:38 +05:00
Alex Ant b3c6967ed9 update 2025-06-13 20:18:34 +05:00
Alex Ant 9a528b17e8 update 2025-06-13 20:15:39 +05:00
Alex Ant 4532932749 back to hash routing 2025-06-13 19:48:36 +05:00
Alex Ant 639a8e2f35 update 2025-06-13 19:20:02 +05:00
Alex Ant 56c2ab38c6 looking for bug 2025-06-13 17:08:27 +05:00
Alex Ant 9769cc0ed4 enable test mode 2025-06-13 16:15:50 +05:00
Alex Ant 96d66b2205 Обновлено использование индекса cooperatives в shared_registrator.hpp, добавлено новое действие delmeet в meet для удаления собраний. Исправлены проверки на наличие активных пайщиков и добавлено форматирование ссылок в компонентах голосования и повестки. Обновлены формы создания и перезапуска собраний для поддержки новых требований. 2025-06-13 13:26:32 +05:00
Alex Ant fea73109ca Добавлено использование функции parseLinks для форматирования ссылок в контексте и решениях в компонентах повестки и голосования. Упрощен код за счет удаления дублирующей функции parseLinks из компонентов. 2025-06-12 20:26:43 +05:00
Alex Ant e39c15c16f Добавлено форматирование ссылок в повестке собрания. Реализована функция для преобразования текста с ссылками в HTML-формат. Исправлено отображение контекста повестки. 2025-06-12 20:22:33 +05:00
Alex Ant 2a13f60bbd Добавлено новое поле 'level' в интерфейсы и DTO для обработки собраний, обновлены адаптеры для поддержки этого поля. Пофиксена проблема с Float на проценте кворума. 2025-06-12 20:14:55 +05:00
Alex Ant d8e9738d71 fix count 2025-06-12 19:17:45 +05:00
Alex Ant f38b78f821 подсчитываем количество активных пайщиков в кооперативах 2025-06-12 15:47:27 +05:00
Alex Ant 9c21630295 meet fix 2025-06-12 15:45:12 +05:00
Alex Ant ea502727ba добавлено действие migrate в meet и созданы миграции на добавление новых шаблонов 2025-06-12 14:56:42 +05:00
Alex Ant 72f4999162 release 2025-06-12 11:13:51 +05:00
Alex Ant adf1dbe635 Добавлены новые зависимости moment-timezone и @novu/js, обновлены версии существующих пакетов. Внесены изменения в модули и сервисы для поддержки новых функциональностей, включая адаптеры для расширений и обработку уведомлений. Реализована логика работы с временными зонами и обновлены интерфейсы для работы с аккаунтами и собраниями. 2025-06-11 21:39:13 +05:00
Alex Ant af2cdb1ca1 Добавлены новые поля для ответов голосования в схемы и DTO, а также обновлены интерфейсы и типы для поддержки голосования на собраниях. Реализована логика обработки ответов и обновлены компоненты для работы с новыми данными. Добавлена поддержка часового пояса в форматирование дат. 2025-06-10 14:14:44 +05:00
Alex Ant e499c0e990 Обновлены компоненты рабочего стола: добавлены маршруты по умолчанию для рабочих столов "participant" и "soviet", реализована логика выбора рабочего стола на основе прав пользователя и сохраненного выбора. Также добавлены новые методы для навигации и сохранения состояния рабочего стола. Исправлены ошибки в компонентах и улучшена верстка. 2025-06-09 17:54:33 +05:00
Alex Ant 206ab6793f almost works 2025-06-09 15:27:03 +05:00
Alex Ant e207c90fd4 add exampleData 2025-06-03 13:12:35 +05:00
Alex Ant c9864008a3 update 2025-06-03 10:54:14 +05:00
Alex Ant 5c89b27a87 update 2025-06-02 23:15:51 +05:00
Alex Ant 3c482ba017 update cooptypes and factory 2025-06-02 23:00:32 +05:00
Alex Ant 2d684411d4 Добавлена поддержка часового пояса в компоненты создания и перезапуска собраний. Обновлены метки для отображения времени с учетом часового пояса. Добавлены зависимости moment-timezone и обновлены конфигурации окружения. 2025-05-30 22:54:22 +05:00
Alex Ant 408ee36a8b Поправлена верстка. Обновлены компоненты для отображения новых данных о вопросах и результатах голосования. Изменен SDK для корректной мульти-подписи документа. 2025-05-30 21:42:07 +05:00
Alex Ant d9efbad80d Добавлены поля для председателя и секретаря в интерфейсы и DTO собраний, а также обновлены соответствующие селекторы и агрегаты документов. Введены сертификаты для председателя и секретаря, обновлены зависимости и исправлены ссылки на информацию о пользователях в документах. 2025-05-23 17:48:52 +05:00
Alex Ant 92e5c9f71a Добавлены новые типы сертификатов пользователей (EntrepreneurCertificate, IndividualCertificate, OrganizationCertificate, RepresentedByCertificate) и обновлены соответствующие DTO и интерфейсы. Обновлены зависимости в модулях и исправлены ссылки на информацию о подписантах в документах. 2025-05-23 14:14:56 +05:00
Alex Ant baef88be50 expandableDocument for meet 2025-05-23 10:49:03 +05:00
Alex Ant 7eff6ac504 meet aggregation DTO 2025-05-22 17:51:29 +05:00
Alex Ant a3ea4d4e18 chore(release): publish 2025-05-14 16:16:51 +05:00
Alex Ant f12047e36f повторная миграция соглашений 2025-05-14 15:41:34 +05:00
Alex Ant c77f37cc43 chore(release): publish 2025-05-14 12:45:52 +05:00
Alex Ant 8bc463b6d6 Обновлен changelog для версии v2025.5.14. 2025-05-14 12:22:46 +05:00
Alex Ant 953429f0da Добавлена поддержка смены темы (светлая/темная) с сохранением в localStorage, обновлены соответствующие компоненты и стили. Исправлено отображение данных участников в таблицах. 2025-05-14 12:12:00 +05:00
Alex Ant 8598050931 Добавлено поле аккаунта в тип Payment и обновлены соответствующие сущности и DTO, а также интерфейс для отображения ФИО плательщика. 2025-05-13 18:15:21 +05:00
Alex Ant 81566674a8 chore(release): publish 2025-05-13 14:56:31 +05:00
Alex Ant aba9f88352 factory bugs fix 2025-05-13 10:19:44 +05:00
Alex Ant 0093c6ddf7 fix bug on dinamic import 2025-05-13 09:10:04 +05:00
Alex Ant cd5a0c2fbc процесс голосования через подпись номера решения 2025-05-12 10:41:37 +05:00
Alex Ant b1c803d2f1 almost done 2025-05-09 17:31:41 +05:00
Alex Ant 3883b68669 SDK компилируется 2025-05-07 08:23:59 +05:00
Alex Ant 5111bb12cf Merge branch 'dev' into document2 2025-05-05 18:56:04 +05:00
Alex Ant cc2518a346 chore(release): publish 2025-05-05 18:55:34 +05:00
Alex Ant 6e98f4c953 update version 2 2025-05-05 18:55:01 +05:00
Alex Ant 8990b25970 update version 2025-05-05 18:53:25 +05:00
Alex Ant c0cdde8685 Merge branch 'testnet' 2025-05-05 18:50:23 +05:00
Alex Ant 7a7e20e4c2 откатываем новую таблицу кооперативов 2025-05-05 18:49:08 +05:00
Alex Ant 743ccd27b6 контракты скомпилировались 2025-05-05 18:46:44 +05:00
Alex Ant 155d9110c5 before contract migrate 2025-05-05 17:25:56 +05:00
Alex Ant 651e0b3445 chore(release): publish 2025-05-05 12:53:42 +05:00
Alex Ant 82f438cbe4 coop migration 2025-05-05 12:28:54 +05:00
Alex Ant c3c30b4e20 chore(release): publish 2025-05-05 11:17:29 +05:00
Alex Ant 8b4889ce83 Функционал миграций по версиям с интеграцией блокчейна и двух баз данных 2025-05-04 14:17:27 +05:00
Alex Ant 7ccaa0390d chore(release): publish 2025-05-04 12:42:52 +05:00
Alex Ant 5f0ed73d0d fix workflow #2 2025-05-04 12:42:23 +05:00
Alex Ant 54518b63d0 update publish workflow 2025-05-04 12:39:52 +05:00
Alex Ant 1c38f2e5fd update version 2025-05-04 12:37:53 +05:00
Alex Ant 7ba12707e1 chore(release): publish 2025-05-04 12:32:16 +05:00
Alex Ant 01992b26f4 fix workflows 2025-05-04 12:26:07 +05:00
Alex Ant 8670ba08d5 chore(release): publish 2025-05-04 12:08:16 +05:00
Alex Ant 67698757cf publish workflow 2025-05-04 12:07:22 +05:00
Alex Ant 833ef3f5d3 Обновление структуры signature_info: добавлен идентификатор подписи. Исправлено условие фильтрации истекших решений в ChairmanPlugin. 2025-05-04 11:40:00 +05:00
Alex Ant b104f14899 create document2 format 2025-05-04 11:02:25 +05:00
Alex Ant 60c86b1db8 chore(release): publish 2025-05-03 16:19:40 +05:00
Alex Ant b6d2965962 Дефолтные конфиги для расширений, фиксы визуалов, микросервис отмены вопроса с повестки 2025-05-03 15:56:08 +05:00
Alex Ant 1548552af3 chore(release): publish 2025-05-02 10:40:41 +05:00
Alex Ant 002cf8025b update 2025-05-01 22:51:07 +05:00
Alex Ant dfd7e4b62c update 2025-05-01 22:46:58 +05:00
Alex Ant e54380cd81 update 2025-05-01 22:29:40 +05:00
Alex Ant 09b3532793 update 2025-05-01 22:28:01 +05:00
Alex Ant b36e288958 update 2025-05-01 22:23:56 +05:00
Alex Ant bcd3c2739a update 2025-05-01 22:21:00 +05:00
Alex Ant 695e653461 update 2025-05-01 22:17:07 +05:00
Alex Ant b068ff810c update 2025-05-01 22:13:38 +05:00
Alex Ant 1a57f7a047 update lock-file 2025-05-01 21:57:50 +05:00
Alex Ant 90f955e48e update 2025-05-01 21:54:59 +05:00
Alex Ant 14fbce5a6b docs #2 2025-05-01 21:52:49 +05:00
Alex Ant 5cff407379 docs 2025-05-01 21:50:39 +05:00
Alex Ant 79b7ff21f5 Удалены отладочные логи из функций входа и выхода пользователя, а также обновлен способ проверки переменных окружения в функции работы с IndexedDB. 2025-05-01 18:23:56 +05:00
Alex Ant 65996a40e9 update 2025-05-01 16:46:36 +05:00
Alex Ant cf3566255a Добавлены отладочные логи в функции входа и выхода пользователя, а также обновлен способ загрузки переменных окружения в конфигурации Quasar для режима разработки. 2025-05-01 16:00:45 +05:00
Alex Ant 582c6fa36d Удалены отладочные логи из функции получения переменных окружения и обновлен middleware для инъекции переменных окружения в браузер с использованием ssrMiddleware. 2025-05-01 14:33:41 +05:00
Alex Ant aefba8b4df update 2025-05-01 13:42:00 +05:00
Alex Ant e43674fd29 Изменен способ определения переменных окружения в конфигурации Quasar: теперь они устанавливаются только для клиентской стороны, если режим не SSR. 2025-05-01 13:27:05 +05:00
Alex Ant 3856826e4d update 2025-05-01 11:34:33 +05:00
Alex Ant 00ed0b7691 update 2025-05-01 11:22:00 +05:00
Alex Ant aa456f6cff update 2025-05-01 11:12:30 +05:00
Alex Ant 3a9dfa643e update 2025-05-01 11:01:19 +05:00
Alex Ant 28580114da update 2025-05-01 10:31:01 +05:00
Alex Ant 8d47f118dd update 2025-05-01 10:29:53 +05:00
Alex Ant d7b45157ff update 2025-05-01 10:27:41 +05:00
Alex Ant db8a48284f update 2025-05-01 10:24:33 +05:00
Alex Ant b00b8d6ca3 update 2025-05-01 09:59:02 +05:00
Alex Ant 22b3d8f691 update 2025-05-01 09:51:43 +05:00
Alex Ant 432c1cd476 update 2025-05-01 09:41:37 +05:00
Alex Ant ed8e4a059a Обновление Dockerfile: замена команды установки зависимостей на принудительную, улучшение структуры образа. Изменение конфигурации GitHub Actions для отключения кеширования и упрощения сборки образов. 2025-05-01 09:36:57 +05:00
Alex Ant 571c1e31ac Оптимизация Dockerfile: добавление этапа сборки для зависимостей, упрощение копирования файлов и улучшение структуры образа. Обновление конфигурации GitHub Actions для сборки и публикации образов с использованием Docker Buildx. 2025-04-30 21:49:16 +05:00
Alex Ant b294d0eea0 Добавление шагов для отладки в GitHub Actions: вывод последних коммитов, текущей ветки и содержимого компонентов. Обновление комментариев и улучшение сборки образов без кеша. 2025-04-30 21:32:51 +05:00
Alex Ant 0b50fbc55d update 2025-04-30 21:29:50 +05:00
Alex Ant f5d5534290 update 2025-04-30 20:54:13 +05:00
Alex Ant 777eb7e398 Добавление middleware для инъекции переменных окружения в window.__ENV__ и рефакторинг функции получения переменных окружения с учетом различных сред (SSR, SPA). Теперь переменные окружения экспортируются через единую функцию getEnv(). 2025-04-30 20:53:02 +05:00
Alex Ant 9b1be55a9e Обновление конфигурации проекта: замена использования переменных окружения на новый модуль env, упрощение Dockerfile, улучшение сборки контейнеров и исправление мелких ошибок в компонентах. 2025-04-30 20:30:42 +05:00
Alex Ant ef4a7d1fa1 update 2025-04-30 18:37:23 +05:00
Alex Ant e6a7380aa5 update 2025-04-30 18:00:07 +05:00
Alex Ant 2f41591339 update 2025-04-30 17:47:08 +05:00
Alex Ant 8916ef0207 update 2025-04-30 17:45:28 +05:00
Alex Ant c3288f765e update 2025-04-30 17:35:42 +05:00
Alex Ant 11d631bee3 update 2025-04-30 17:33:58 +05:00
Alex Ant e3be78edb0 update 2025-04-30 17:29:37 +05:00
Alex Ant 59f01a8426 update 2025-04-30 17:17:55 +05:00
Alex Ant 76b7c8ef3b update 2025-04-30 17:05:31 +05:00
Alex Ant fbaae9ce76 update 2025-04-30 16:53:55 +05:00
Alex Ant e70b58a3df print env 2025-04-30 16:47:47 +05:00
Alex Ant ec551c9de8 VITE_ prefix 2025-04-30 16:39:33 +05:00
Alex Ant 7a8cb5835a правки SSR проблема рендиринга 2025-04-30 15:55:07 +05:00
Alex Ant 3b8ccf173b modify quasar conf 2025-04-30 12:49:12 +05:00
Alex Ant 172ce29665 update 2025-04-30 11:32:47 +05:00
Alex Ant e7d8a8d2c0 хук на деплой 2025-04-30 10:29:59 +05:00
Alex Ant cc7b43f4ba Добавление сборки и публикации нового Docker-образа для приложения @coopenomics/desktop в workflow. Обновление конфигурации сборки контейнеров. 2025-04-29 23:23:13 +05:00
Alex Ant 71425977f5 Обновление Dockerfile для упрощения сборки с использованием lerna. Добавление новых прокси-файлов для модулей @dicebear/core, @dicebear/collection и email-regex. Обновление зависимостей в package.json и pnpm-lock.yaml. Изменение конфигурации Quasar для оптимизации работы с новыми модулями. 2025-04-29 23:21:10 +05:00
Alex Ant 4549727d0b update workflow 2025-04-29 21:49:48 +05:00
Alex Ant e030d97059 workflow initialization 2025-04-29 21:40:51 +05:00
Alex Ant 13c1ca4f79 Merge branch 'main' into dev 2025-04-29 16:32:03 +05:00
Alex Ant 637d7c0db1 chore(release): publish 2025-04-29 16:27:09 +05:00
Alex Ant 7513a4b6d6 Merge branch 'testnet' 2025-04-29 16:21:40 +05:00
Alex Ant 76100ef07d update script 2025-04-29 16:21:22 +05:00
Alex Ant ab139209db update templates 2025-04-29 16:17:58 +05:00
Alex Ant c6a31baaab Добавление нового поля 'type' в сущность Payment и соответствующие изменения в DTO, схемах и селекторах. Обновление логики обновления статусов платежей с учетом нового поля. Исправление параметров в методах для получения заказов. 2025-04-29 13:36:04 +05:00
Alex Ant 7c9d4629b6 Добавление нового поля 'coop' в интерфейс Model и обновление схемы валидации для SelectBranchStatement. Обновление логики комбинирования данных в классе Factory для включения данных о кооперативе. Комментарии в стилях инпутов переведены в закомментированный вид. 2025-04-29 12:25:08 +05:00
Alex Ant 986858c20d Обновление скриптов публикации и логики миграции. Изменены команды для публикации на продакшн, добавлен новый скрипт publish-prod.sh. Обновлена логика удаления кандидатов в функции миграции и исправлены ссылки на индексы кандидатов в confirmreg.cpp. 2025-04-29 11:05:03 +05:00
Alex Ant a0551095dc lerna update 2025-04-29 10:16:02 +05:00
Alex Ant d0804c886a disable meet for temp 2025-04-29 10:11:14 +05:00
Alex Ant 1befca7e28 Добавление новых скриптов для развертывания и обновление интерфейсов для обработки голосования на общем собрании. Обновлены типы данных в интерфейсах и DTO, добавлены новые методы для генерации документов и улучшения функционала. Удалены устаревшие интерфейсы и компоненты, улучшена структура кода для повышения эффективности. 2025-04-28 23:55:55 +05:00
Alex Ant 3d4482157a Удаление устаревших интерфейсов и таблиц, связанных с кошельками. Обновление логики обработки платежей и интерфейсов для работы с новыми типами данных. Улучшение структуры компонентов и интерфейсов для более эффективного взаимодействия с API. Обновление стилей и компонентов пользовательского интерфейса для улучшения визуального восприятия. 2025-04-26 17:14:22 +05:00
Alex Ant 3cd71f1cd4 Обновление интерфейсов и DTO для работы с документами и собраниями. Добавлены новые поля и типы данных, улучшена обработка документов в сервисах. Удалены устаревшие селекторы и обновлены существующие для соответствия новым требованиям. Исправлены типы данных в селекторах и добавлены новые экспорты. 2025-04-25 23:44:32 +05:00
Alex Ant eebf443c1d Сейчас будем переводить сервис документов на агрегатор. Обновление интерфейсов и DTO для обработки документов. Изменены типы полей в интерфейсах DocumentPackageDomainInterface, DocumentRepository и DocumentDomainService для поддержки значений null. Добавлены проверки на наличие данных в DocumentDomainEntity и улучшена обработка документов в DocumentDomainService. Обновлены методы для работы с документами в API и хранилище. 2025-04-23 19:03:18 +05:00
Alex Ant 7aaf0b9375 Первичная мобильная верстка страниц стола совета 2025-04-23 12:39:23 +05:00
Alex Ant 5ff9675e60 Обновление конфигурации и добавление тестового режима для собраний. Изменен порт для state-history-endpoint, добавлен флаг TEST_MODE в контракте meet, обновлены проверки дат открытия и закрытия собраний. Обновлены интерфейсы и DTO для обработки новых типов данных и улучшения функционала. 2025-04-22 23:23:09 +05:00
Alex Ant 646390edff Добавление функционала для генерации бюллетеней голосования на общем собрании. Обновлены интерфейсы и DTO для обработки новых типов документов, добавлены методы для генерации бюллетеней и голосования. Исправлены типы данных для идентификаторов вопросов повестки. 2025-04-21 20:29:12 +05:00
Alex Ant b1958c5442 Добавление новых методов для подписания решений председателем и секретарем на общем собрании. Удален метод закрытия собрания, обновлены интерфейсы и DTO для обработки новых типов документов и действий. 2025-04-21 16:44:27 +05:00
Alex Ant 01b9590e81 Добавление новых типов и методов для работы с собраниями в модуле общих собраний. Реализованы методы получения данных о собраниях, обновлены интерфейсы и DTO для обработки информации о голосованиях и документах собраний. 2025-04-20 16:41:20 +05:00
Alex Ant 985a288bf3 Добавление новых входных типов и методов для получения данных о собраниях в модуле общих собраний. Реализованы методы getMeet и getMeets, а также обновлены интерфейсы и DTO для обработки данных. 2025-04-20 12:56:42 +05:00
Alex Ant 01dcfb88e7 Обновление документации и DTO для модуля общих собраний. Добавлены описания для полей в DTO, улучшена структура и добавлены новые типы данных для обработки информации о собраниях и голосованиях. 2025-04-20 11:59:29 +05:00
Alex Ant 76415a8dec Добавление модуля общих собраний и расширение DTO для документов, включая новые интерфейсы и классы для обработки документов собраний и решений. 2025-04-20 11:39:27 +05:00
Alex Ant 586b7c14f8 meet module & extends all documents DTOs 2025-04-18 15:27:35 +05:00
Alex Ant 0ee4bf2b25 update release script 2025-04-16 22:03:36 +05:00
Alex Ant 5673e8abe8 update releases script 2025-04-16 22:02:08 +05:00
Alex Ant c446e32a8a generate changelog releases 2025-04-16 21:42:37 +05:00
Alex Ant eee9392fb4 make Templates correct 2025-04-16 20:08:50 +05:00
Alex Ant 82a3961608 move templates #1 2025-04-16 20:08:24 +05:00
Alex Ant f8689fc409 wtf?! 2025-04-16 20:06:49 +05:00
Alex Ant 7de93e1780 add meet contract, cooptypes and empty documents templates 2025-04-16 19:58:49 +05:00
Alex Ant 19e742b7d1 desktop bug fixs 2025-04-15 15:57:55 +05:00
Alex Ant e3f0250fd2 remove Env.ts file from desktop and move params to .env 2025-04-15 12:27:29 +05:00
Alex Ant e4b39b89f3 fix system contract action name 2025-04-15 10:27:53 +05:00
Alex Ant d2888b49e8 fix contracts build 2025-04-15 10:14:07 +05:00
Alex Ant b97ed49a60 coopStore release 2025-04-11 18:29:07 +05:00
Alex Ant 65936dc85b refactoring desktop 2025-04-10 11:40:14 +05:00
Alex Ant b1d02ee302 claim -> result, result -> assignment 2025-04-06 12:56:55 +05:00
Alex Ant cca47abb9c before make refactoring 2025-04-06 11:25:29 +05:00
Alex Ant c810ba62b4 shared actions 2025-04-05 11:36:06 +05:00
Alex Ant dcce7ffacc loan contract 2025-04-03 18:52:53 +05:00
Alex Ant e9fb137146 contracts refactoring 2025-04-03 09:36:48 +05:00
Alex Ant 7100c9c300 appStore & medusa component & capital contract (start rework) 2025-03-28 18:42:28 +05:00
Alex Ant e9b5496387 refactoring participant widget to page 2025-03-27 19:14:02 +05:00
Alex Ant 87ecde390d chore(release): publish 2025-03-27 18:13:33 +05:00
Alex Ant 8b33c66e22 update mutation simplification 2025-03-27 17:30:31 +05:00
Alex Ant b3bbb6624e make participants editable 2025-03-27 14:32:23 +05:00
Alex Ant 2ddac45612 change decision dto and logout on some auth problems 2025-03-26 22:18:12 +05:00
Alex Ant ddd7d47516 Merge pull request #201 from coopenomics/kamilocean/sprint-4
Kamilocean/sprint 4
2025-03-26 20:09:37 +03:00
Alex Ant a770072809 README.md for cleos wallet 2025-03-26 18:27:05 +05:00
Alex Ant 5b38ce0b37 make cleos separated component 2025-03-26 18:19:52 +05:00
Alex Ant 804708076a make cleos wallet accessable 2025-03-26 13:08:04 +05:00
Alex Ant a0ad71a524 make unnesassary result 2025-03-26 11:42:05 +05:00
Alex Ant 9d03694ea7 some updates on contracts and tests 2025-03-22 13:58:51 +05:00
Alex Ant 7a619e0e9e update 2025-03-21 17:58:33 +05:00
Alex Ant 6bd5eb7930 Merge branch 'dev' into TSK-900 2025-03-19 10:58:53 +05:00
Alex Ant 744d1859d5 Создание кошелька при регистрации участника 2025-03-19 10:58:20 +05:00
Alex Ant 8033e3fc8e update 2025-03-18 21:04:12 +05:00
Alex Ant abb0b629f3 TSK-900 capital contract - fund by membership contributions and distribution it 2025-03-18 11:50:07 +05:00
kamilocean 34a61f49f6 Merge branch 'dev' into kamilocean/sprint-4 2025-03-17 16:07:50 +03:00
kamilocean 08c31171a0 WIP: fix EditableActions instead of ActionButton 2025-03-17 16:07:28 +03:00
Ilia Smirnov 40addbf595 Merged readme fixes 2025-03-17 12:52:02 +03:00
Ilia Smirnov abd6da0a37 Merge branch 'dev' of github.com:coopenomics/mono into TSK-878 2025-03-17 12:49:40 +03:00
Alex Ant 794d1c5019 Merge pull request #217 from coopenomics/dacom-dark-sun/sprint-4
Спринт-4 | dacom-dark-sun
2025-03-17 09:57:34 +03:00
Alex Ant b8d048bf3c README.md 2025-03-17 11:55:18 +05:00
Ilia Smirnov bb7b650ebc docs(install): updated installation instructions 2025-03-17 09:44:10 +03:00
kamilocean 5253de9279 WIP: add EditableOrganizationCard 2025-03-16 21:04:40 +03:00
Alex Ant 094945e350 make it works 2025-03-14 13:20:41 +05:00
kamilocean eb6b58e6db Merge branch 'dev' into kamilocean/sprint-4 2025-03-13 23:54:25 +03:00
kamilocean 7bcb6e30a7 fix: add Zeus type 2025-03-13 23:54:02 +03:00
Alex Ant 7ed4024555 run container on boot 2025-03-13 22:58:46 +05:00
Alex Ant 6fa45c5958 bug fix 2025-03-13 22:39:41 +05:00
Alex Ant a883f140d4 clear database on reboot 2025-03-13 21:04:21 +05:00
Alex Ant 1bec52efcb bug fix #2 2025-03-13 20:50:42 +05:00
Alex Ant 674e58ec3f fix bug 2025-03-13 20:46:53 +05:00
Alex Ant 373d705387 update nodemon for notificator 2025-03-13 20:33:56 +05:00
Alex Ant 46fb693020 add clear method 2025-03-13 20:10:47 +05:00
Alex Ant f1fe7d1545 make boot better 2025-03-13 19:57:35 +05:00
kamilocean 44ab386835 WIP: EditableAccountCard 2025-03-13 00:30:00 +03:00
Alex Ant 51d736eba4 chore(release): publish 2025-03-12 11:33:00 +05:00
Alex Ant dcc4f6bd03 fix packages 2025-03-12 10:31:41 +05:00
Alex Ant eef2482423 README.md and some setup fixs 2025-03-12 10:24:48 +05:00
Alex Ant f46a1fb9b5 ascii text fix 2025-03-12 09:51:52 +05:00
Alex Ant bae45af414 contracts path change 2025-03-12 09:33:47 +05:00
Alex Ant aff3835f50 fix data paths 2025-03-12 09:26:43 +05:00
Alex Ant 5f249f6032 add lossed lib dir 2025-03-12 09:03:45 +05:00
Alex Ant a185d7e9e8 fix build 2025-03-11 23:34:27 +05:00
Alex Ant 3449caf0e2 fix build 2025-03-11 23:15:03 +05:00
Alex Ant cc458cc916 fix some files 2025-03-11 22:59:52 +05:00
Alex Ant 2b6b56ace9 move contracts inside and make common setup script 2025-03-11 22:57:08 +05:00
Alex Ant 4d72c920c6 capital cooptypes 2025-03-11 19:57:49 +05:00
Alex Ant b0186a1baa add Env-testnet.ts 2025-03-06 13:53:31 +05:00
Alex Ant bc3836b316 docker-compose for infra 2025-03-06 11:34:04 +05:00
Alex Ant 0a444efe55 sosediAgreement and docker-compose-infra.yaml 2025-03-06 11:22:43 +05:00
Alex Ant fba3988834 env controller 2025-03-05 21:55:40 +05:00
Alex Ant b99e1abb03 update package 2025-03-05 21:54:10 +05:00
Alex Ant ab44237bb9 update cooptypes 2025-03-05 17:33:48 +05:00
Alex Ant 6d98dc073f add capital contract 2025-03-04 20:23:36 +05:00
Alex Ant 9709ef4333 investment templates 2025-02-25 20:35:03 +05:00
Alex Ant cb60f6f735 update test structure 2025-02-22 15:43:00 +05:00
Alex Ant 5d0ab2e2db fix 2025-02-13 10:14:32 +05:00
Alex Ant 4e3b0b52c8 branch bug fix 2025-02-13 10:08:46 +05:00
Alex Ant 973590281c chore(release): publish 2025-02-10 14:58:11 +05:00
Alex Ant 4f7defb85c update 2025-02-10 14:56:44 +05:00
Alex Ant 59f4d8dc26 delete onewallet structure 2025-02-10 14:44:03 +05:00
Alex Ant be736e105a wallet fast fix 2025-02-10 13:39:31 +05:00
Alex Ant 3be56ba462 chore(release): publish 2025-02-07 19:35:06 +05:00
Alex Ant f7adf8457b Dockerfile fix 2025-02-07 19:25:01 +05:00
Alex Ant 80b8856f15 fix 2025-02-07 18:48:44 +05:00
Alex Ant 0860f47d88 capital sdk mutations 2025-02-07 18:39:39 +05:00
Alex Ant 382b75fccf cooplace 2025-01-30 19:25:35 +05:00
Alex Ant d3dacbd32d add production cooperative to the list 2025-01-28 23:08:02 +05:00
Alex Ant 6c51e4b596 fix selectBranch bug and add IP for entrepreneur user 2025-01-28 16:27:22 +05:00
Alex Ant d0bd4428be chore(release): publish 2025-01-27 11:08:26 +05:00
Alex Ant 43ffcb7362 update 2025-01-27 10:54:50 +05:00
Alex Ant ca5dfca290 update table style on documents 2025-01-27 10:29:08 +05:00
Alex Ant 8a495eff37 add new templates for documents and fix QR-pay interface 2025-01-27 10:07:52 +05:00
Alex Ant bee6af12fb get COOPBACK const from system.info everywhere 2025-01-23 18:52:33 +05:00
Alex Ant 4a3dfc3eb7 update 2025-01-22 17:49:33 +05:00
Alex Ant 4e87a4adc4 fix init process 2025-01-22 16:08:24 +05:00
Alex Ant d9bb9d5884 update system info 2025-01-22 12:23:34 +05:00
Alex Ant 562be0cb89 update 2025-01-21 17:51:03 +05:00
Alex Ant 2fdc86af97 chore(release): publish 2025-01-19 18:52:27 +05:00
Alex Ant 220d1225b2 update 2025-01-19 17:04:34 +05:00
Alex Ant e047a6e449 remove username input on getAccounts & remove deleteAccount mutation on SDK 2025-01-19 16:34:54 +05:00
Alex Ant 97b21a9d69 chore(release): publish 2025-01-18 16:15:43 +05:00
Alex Ant 9be9570dea document and blockchain classes on SDK, move sign documents on signup to use SDK 2025-01-18 16:11:32 +05:00
Alex Ant cbfe37dbba chore(release): publish 2025-01-17 13:52:58 +05:00
Alex Ant bf176a2c05 fix connection button only for voskhod coops 2025-01-17 13:50:36 +05:00
Alex Ant 173c51eb26 connection button for coops on desktop 2025-01-17 13:46:47 +05:00
Alex Ant 71dbb090fb memberButton for access to coop settings 2025-01-17 13:02:40 +05:00
Alex Ant 832133e6cc Canvas SDK class 2025-01-17 12:57:46 +05:00
Alex Ant 2730a92b01 update 2025-01-16 19:54:20 +05:00
Alex Ant 40fb5c80eb update 2025-01-16 19:45:35 +05:00
Alex Ant 6c65095961 add account class 2025-01-16 17:46:08 +05:00
Alex Ant d02f7ae7bc rollback 2025-01-16 12:40:17 +05:00
Alex Ant 9f0b4b24ba update SDK 2025-01-16 12:34:04 +05:00
Alex Ant 237357c1d5 canvas class and update types on dto 2025-01-16 12:30:57 +05:00
Alex Ant aefb1caf57 update 2025-01-16 12:17:00 +05:00
Alex Ant a3328e7ef0 move to sdk login 2025-01-16 12:09:04 +05:00
Alex Ant db24588273 fix paymentMethods orders 2025-01-15 13:47:58 +05:00
Alex Ant 2cabeeb6bd temp fix order id bug 2025-01-15 10:52:02 +05:00
Alex Ant 88352202b0 update 2025-01-14 21:50:45 +05:00
Alex Ant e02d8a949b update 2025-01-14 20:40:26 +05:00
Alex Ant e7e5457cf2 uppdate 2025-01-14 20:39:39 +05:00
Alex Ant 29b98b0f7d add login method to SDK 2025-01-14 20:32:49 +05:00
Alex Ant ae7378f474 update 2025-01-14 18:07:31 +05:00
Alex Ant b05c17bee4 chore(release): publish 2025-01-14 17:50:44 +05:00
Alex Ant a2d3dac226 chore(release): publish 2025-01-14 17:41:40 +05:00
Alex Ant a8ec41e255 fix 2025-01-14 13:48:53 +05:00
Alex Ant 1d16062961 renaming and sdk 2025-01-14 13:45:45 +05:00
Alex Ant 2a614e8656 move to sdk #1 2025-01-14 12:32:58 +05:00
Alex Ant baaaaf01bf sdk-client docs 2025-01-10 10:35:54 +05:00
Alex Ant 20f1fc51b1 hard payment migration 2025-01-01 21:07:59 +05:00
Alex Ant d749ebf981 add a lot of queries and mutations 2025-01-01 12:06:41 +05:00
Alex Ant 04364c503c chore(release): publish 2024-12-24 23:43:08 +05:00
Alex Ant ae2a040fe4 free decision 2024-12-24 22:45:50 +05:00
Alex Ant 0debf23b5e move to a documented ql-client 2024-12-23 13:45:49 +05:00
Alex Ant 55e7849b43 visual fixs 2024-12-21 18:37:31 +05:00
Alex Ant 34d9a73677 Merge branch 'dev' into testnet 2024-12-20 21:04:35 +05:00
Alex Ant 0b9ccf5bc0 update 2024-12-20 21:04:07 +05:00
Alex Ant 48e72bb9df update 2024-12-20 21:03:36 +05:00
Alex Ant 35aed44bcb update card and add selectors for generate free decision and selectBranch documents 2024-12-20 21:02:19 +05:00
Alex Ant e4cf693c0d Merge branch 'testnet' 2024-12-20 16:47:35 +05:00
Alex Ant f0755f5f90 update 2024-12-20 16:47:29 +05:00
Alex Ant bdfc6af688 selectors update coopjs 2024-12-20 16:26:26 +05:00
Alex Ant 31b4061a43 resolver of free decision 2024-12-20 14:44:20 +05:00
Alex Ant a1b80f0323 drafts migration complete 2024-12-18 13:36:52 +05:00
Alex Ant 1678686ce7 freeDecision and projectFreeDecision document templates 2024-12-18 13:29:10 +05:00
Alex Ant c25d05196d generate selectBranch document throw graphql 2024-12-16 20:16:44 +05:00
Alex Ant bdddc7ad03 selectBranch for added members 2024-12-14 21:09:13 +05:00
Alex Ant 1d1ad4f9fa branches 2024-12-11 21:01:22 +05:00
Alex Ant 099fcc7981 update! 2024-12-05 19:00:58 +05:00
Alex Ant 2ef44e45f6 from 2024-12-03 20:19:36 +05:00
Alex Ant ebe62d0498 migrate 2024-12-03 19:11:46 +05:00
Alex Ant 6472b20ea4 branches auto enable 2024-12-03 14:00:11 +05:00
Alex Ant 69cdb2d754 enable / disable branches 2024-12-02 16:11:05 +05:00
Alex Ant f7d8000b48 coopjs mutations and queries for branches 2024-11-29 21:10:54 +05:00
Alex Ant a44afbe1b9 make branches happen #1 2024-11-19 22:19:26 +05:00
Alex Ant 662da1b8a9 update 2024-11-15 16:24:39 +05:00
Alex Ant 2a3d743204 router refactoring 2024-11-14 20:30:39 +05:00
Alex Ant 7241ee4c7a pre-release 2024-11-14 20:08:56 +05:00
Alex Ant 5c084d6e8b add reflect-metadata 2024-11-10 20:03:16 +05:00
Alex Ant 1060c7fdfc package fix 2024-11-10 19:53:15 +05:00
Alex Ant b5d6c0e0b3 fix bug on parser with return function 2024-11-10 17:42:59 +05:00
Alex Ant d69644350e integration coopjs & terminal 2024-11-10 17:33:29 +05:00
Alex Ant 8634622a6a coopjs 0.01 2024-11-09 21:24:29 +05:00
Alex Ant cc73554350 graphql & apollo server & guards & documentator prototype 2024-11-07 21:06:17 +05:00
Alex Ant 8adf93d592 graphql implementation 2024-11-07 19:42:17 +05:00
Alex Ant 6bd60ddf96 extensions #3 2024-11-07 12:43:33 +05:00
Alex Ant ea5bcbe4dd extensions #2 2024-11-07 10:38:36 +05:00
Alex Ant 541b49069d nestjs & postgres migration #1 2024-11-06 10:54:38 +05:00
Alex Ant ba868866ec postgres initialization 2024-11-04 12:48:58 +05:00
Alex Ant 606ae48f13 update 2024-11-04 11:54:33 +05:00
Alex Ant 09c5445f83 nestjs but fix 2024-11-04 11:46:26 +05:00
Alex Ant 4a0a18a7b0 nestjs integration 2024-11-03 20:18:40 +05:00
Alex Ant ed9d1ab738 test 2024-11-03 14:25:08 +05:00
Alex Ant a61e8084dd fix 2024-11-03 14:13:39 +05:00
Alex Ant e169380178 make settings visible only for logged in 2024-11-03 14:09:15 +05:00
Alex Ant b07d4ef6c3 fix cooperative settings for everone 2024-11-03 13:49:39 +05:00
Alex Ant 4c713c7652 make common header layout and better settings menu 2024-11-03 13:22:24 +05:00
Alex Ant 90e8c6b3c4 chore(release): publish 2024-10-30 19:49:43 +05:00
Alex Ant 07bf05cb2c normal plugin model with some payment plugins 2024-10-30 19:42:48 +05:00
Alex Ant 49d29902a8 update 2024-10-29 23:42:49 +05:00
Alex Ant 32a90c2a9e controller-next initialization 2024-10-29 23:42:14 +05:00
Alex Ant 16ed2c1517 support 2024-10-29 11:50:49 +05:00
Alex Ant 8bb0f1c799 chore(release): publish 2024-10-28 21:49:21 +05:00
Alex Ant f14fe2dd64 update cardcoop 2024-10-28 20:45:08 +05:00
Alex Ant 884f0ee0de changeAuthorizedHome 2024-10-28 19:47:55 +05:00
Alex Ant 744270f48c update 2024-10-28 19:42:04 +05:00
Alex Ant c30849be3c cardcoop on a main screen 2024-10-28 19:06:15 +05:00
Alex Ant f295ac8b4d separated settings page 2024-10-28 17:56:40 +05:00
Alex Ant 9469a8f43d update 2024-10-28 14:18:07 +05:00
Alex Ant 786799ca40 update 2024-10-28 14:16:53 +05:00
Alex Ant aa6238cf5a fix 2024-10-28 13:38:54 +05:00
Alex Ant 1ed31ee2e2 update 2024-10-28 13:26:42 +05:00
Alex Ant 7d8c12977c generateOptions for Documents 2024-10-28 13:15:07 +05:00
Alex Ant 81ee1d63a6 Merge branch 'main' into dev 2024-10-28 11:59:00 +05:00
Alex Ant cf1c1b3198 chore(release): publish 2024-10-28 11:55:43 +05:00
Alex Ant bc7b1e8472 update 2024-10-28 11:55:02 +05:00
Alex Ant 7319c41cc1 chore(release): publish 2024-10-28 11:51:09 +05:00
Alex Ant 2f09fc32c0 finish bugfix 2024-10-28 11:50:41 +05:00
Alex Ant f85b3f54a1 chore(release): publish 2024-10-28 10:49:06 +05:00
Alex Ant 1a68669d6d update Dockerfile 2024-10-28 10:48:04 +05:00
Alex Ant 6345c2d414 chore(release): publish 2024-10-28 10:16:08 +05:00
Alex Ant 87930cad75 update 2024-10-28 10:14:41 +05:00
Alex Ant 3ab2232121 Dockerfile 2024-10-28 10:06:40 +05:00
Alex Ant 9719e25421 move to weasyprint 2024-10-28 10:03:29 +05:00
Alex Ant 8e1f998c39 try to fix it ! 2024-10-27 20:34:08 +05:00
Alex Ant deb1c224f8 update 2024-10-27 19:33:06 +05:00
Alex Ant b2fa79898a arial embded font 2024-10-27 17:56:49 +05:00
Alex Ant da2759a3c6 update 2024-10-27 15:29:12 +05:00
Alex Ant f6bc696426 add common Arial font 2024-10-27 15:09:17 +05:00
Alex Ant da653e9b32 looking for bug #2 2024-10-27 12:46:47 +05:00
Alex Ant 227e153bde looking for bug 2024-10-27 12:03:18 +05:00
Alex Ant 12f906b9b0 update 2024-10-26 21:09:25 +05:00
Alex Ant c8236d4d10 update 2024-10-26 21:01:26 +05:00
Alex Ant e2006da50d TSK-289 Устранить избыточное сохранение документа при регенерации (1) 2024-10-26 20:20:05 +05:00
Alex Ant 433a7d3641 chore(release): publish 2024-10-26 17:45:45 +05:00
Alex Ant 6b41c74b43 regenerate document button, some bugs and fixs 2024-10-26 17:38:12 +05:00
Alex Ant cc3e7ff7c6 fix bug auto powerup on every restart 2024-10-26 13:42:11 +05:00
Alex Ant a35a6bf642 separate init payment factory 2024-10-26 13:10:52 +05:00
Alex Ant 9ecd523646 fix double subscriber bug 2024-10-26 12:52:24 +05:00
Alex Ant e7f896c38e update notification template 2024-10-26 10:49:28 +05:00
Alex Ant 624ec743b1 fix bug loading button 2024-10-25 19:26:41 +05:00
Alex Ant 553c5745ef fix update soviet bug 2024-10-25 16:46:26 +05:00
Alex Ant 3f2779ca3d fix bug voskhod everywhere 2024-10-25 16:42:18 +05:00
Alex Ant e51b962627 databazor bug fix 2024-10-25 16:20:58 +05:00
Alex Ant f709e135b6 Merge branch 'testnet' 2024-10-25 11:10:33 +05:00
Alex Ant 50b48aa247 update 2024-10-24 11:44:05 +05:00
Alex Ant 508f2abc82 update 2024-10-24 11:37:39 +05:00
Alex Ant 42ec56e578 fix 2024-10-24 11:26:07 +05:00
Alex Ant 92673dac6e chore(release): publish 2024-10-23 21:21:41 +05:00
Alex Ant daf57aba35 fix 2024-10-23 21:21:00 +05:00
Alex Ant dee629c429 chore(release): publish 2024-10-23 21:16:50 +05:00
Alex Ant 67f9092350 fix lib 2024-10-23 21:15:52 +05:00
Alex Ant 88691d47a5 chore(release): publish 2024-10-23 21:02:47 +05:00
Alex Ant 0fdd9bc803 update 2024-10-23 21:02:25 +05:00
Alex Ant 8452c607b4 chore(release): publish 2024-10-23 20:57:27 +05:00
Alex Ant 4fc57c2d57 update 2024-10-23 20:56:58 +05:00
Alex Ant 9f0b707a30 chore(release): publish 2024-10-23 20:51:30 +05:00
Alex Ant 511bc351d5 publish 2024-10-23 20:49:38 +05:00
Alex Ant 56ee3e962c chore(release): publish 2024-10-23 20:42:13 +05:00
Alex Ant 2781e8519d fix 2024-10-23 20:40:34 +05:00
Alex Ant 46575348fe chore(release): publish 2024-10-23 20:24:23 +05:00
Alex Ant bae2ca646b publish again 2024-10-23 20:24:00 +05:00
Alex Ant 0686c6ab00 chore(release): publish 2024-10-23 20:20:51 +05:00
Alex Ant db04b66ce5 update 2024-10-23 20:20:25 +05:00
Alex Ant c43c8a29af chore(release): publish 2024-10-23 20:17:40 +05:00
Alex Ant aaea18abe1 publish 2024-10-23 20:16:35 +05:00
Alex Ant 0b6076cb61 chore(release): publish 2024-10-23 20:10:05 +05:00
Alex Ant 3b6d02f02c fix 2024-10-23 20:08:45 +05:00
Alex Ant 625a0586a3 public 2024-10-23 20:06:22 +05:00
Alex Ant 10d63ca586 powerup is private plugin 2024-10-23 20:06:01 +05:00
Alex Ant d2697bf9de make library from terminal 2024-10-23 20:04:34 +05:00
Alex Ant fa8c8843e2 make powerup private plugin 2024-10-19 22:07:20 +05:00
Alex Ant 7b59ea4b96 chore(release): publish 2024-10-19 22:03:06 +05:00
Alex Ant 058215934e Merge branch 'testnet' 2024-10-19 22:02:08 +05:00
Alex Ant 1d724d841f plugin factory and powerup plugin 2024-10-19 21:58:34 +05:00
Alex Ant 32db2100de implementation plugins worker system 2024-10-18 11:27:39 +05:00
Alex Ant 095c77b65b chore(release): publish 2024-10-17 16:20:02 +05:00
Alex Ant c1c07bff8f plugin factory and powerup plugin sketch 2024-10-17 16:18:39 +05:00
Alex Ant 1206bd0e98 fix voskhod everywhere bug 2024-10-17 13:22:35 +05:00
Alex Ant 67bcd1b307 update text on install 2024-10-17 10:52:06 +05:00
Alex Ant 31ef70e433 health check 2024-10-16 13:56:37 +05:00
Alex Ant afb12961d2 fix launch errors 2024-10-16 13:38:08 +05:00
Alex Ant 3dbd40e334 bug fix soviet update 2024-10-16 11:10:18 +05:00
Alex Ant bc5d6e38c8 console.error(e 2024-10-15 23:37:27 +05:00
Alex Ant 5a39143051 openReplay connection 2024-10-14 21:24:45 +05:00
Alex Ant 18e9571877 fix css bug 2024-10-13 16:52:55 +05:00
Alex Ant a828f4c831 chore(release): publish 2024-10-13 16:26:37 +05:00
Alex Ant 54ac12f250 update migrations 2024-10-13 16:24:26 +05:00
Alex Ant 9a6a72f605 feat: запрос соглашений
fix: интерфейс
2024-10-13 16:13:52 +05:00
Alex Ant 03949489e8 docs: добавлен файл конвенции коммитов 2024-10-13 13:19:16 +05:00
Alex Ant 8ebd735e7e update 2024-10-13 13:08:59 +05:00
Alex Ant 39246da73f update amount in agreement and fix bug in terminal 2024-10-13 12:00:39 +05:00
Alex Ant bf33f60368 cooperative connection 2024-10-13 11:50:22 +05:00
Alex Ant 492a613769 fix bugs 2024-10-12 00:59:58 +05:00
Alex Ant 2c02c3434e update 2024-10-12 00:51:37 +05:00
Alex Ant a186ddd9d2 chore(release): publish 2024-10-12 00:46:06 +05:00
Alex Ant 4b0c7a5e4e update 2024-10-12 00:45:35 +05:00
Alex Ant 54cfbe3ab6 fix 2024-10-12 00:39:07 +05:00
Alex Ant 02015cf0b8 update migrator package.json 2024-10-12 00:37:39 +05:00
Alex Ant 416e4d3598 interface rework & documents style change 2024-10-12 00:31:52 +05:00
Alex Ant e0d9c4b0ea make migrator private 2024-10-10 20:55:46 +05:00
Alex Ant 2659e3bc09 migrator release 2024-10-10 20:54:27 +05:00
Alex Ant d296167b6a agreementChecker fix, payment description fix, loader on add user 2024-10-10 20:41:18 +05:00
Alex Ant 89b0aa7fec chore(release): publish 2024-10-10 18:38:19 +05:00
Alex Ant 787aadf444 fix bugs 2024-10-10 18:09:22 +05:00
Alex Ant d67161a29b slice secret 2024-10-10 15:02:12 +05:00
Alex Ant 7f4777ead4 правка текста вступительного взноса 2024-10-10 14:41:26 +05:00
Alex Ant 1e2147b143 fix aggregation 2 2024-10-10 12:09:10 +05:00
Alex Ant 9f0a2fbf63 chore(release): publish 2024-10-10 11:28:11 +05:00
Alex Ant 7804851bc9 update agregate pipeline 2024-10-10 11:15:47 +05:00
Alex Ant adc50dd89e chore(release): publish 2024-10-09 22:20:55 +05:00
Alex Ant 5378cf5ddc template fix 2024-10-09 22:14:11 +05:00
Alex Ant a733bb605f fix model 2024-10-09 14:17:19 +05:00
Alex Ant aaa1b5a264 test update 2024-10-09 14:01:21 +05:00
Alex Ant 5855cdee65 install process 2024-10-09 13:46:08 +05:00
Alex Ant c0d584e644 TSK-225 vaultModel and wif store for cooperative operations 2024-10-04 12:01:44 +05:00
Alex Ant 955f0f473e fix bug 2024-09-30 23:10:59 +05:00
Alex Ant 9ceb888124 update 2024-09-30 22:13:59 +05:00
Alex Ant e902933693 update 2024-09-30 21:43:41 +05:00
Alex Ant e07b47fb10 update 2024-09-30 21:37:54 +05:00
Alex Ant 5bf08d9701 update 2024-09-30 21:33:02 +05:00
Alex Ant 597fa1e6fa update package 2024-09-30 21:21:45 +05:00
Alex Ant dda3ec0ba0 chore(release): publish 2024-09-30 21:09:57 +05:00
Alex Ant 991f08c749 dompurify and coopback <br> fix 2024-09-30 21:08:26 +05:00
Alex Ant 923865cd7c bug fix #3 2024-09-30 20:00:25 +05:00
Alex Ant 606aee8ccd chore(release): publish 2024-09-30 17:24:04 +05:00
Alex Ant 4a1cb27d0a big bug #2 2024-09-30 17:21:38 +05:00
Alex Ant 26cd7f3a12 chore(release): publish 2024-09-30 17:09:39 +05:00
Alex Ant f4045dbc56 chore(release): publish 2024-09-30 17:07:54 +05:00
Alex Ant 33c2b24550 fix bug of parallel generation 2024-09-30 17:06:17 +05:00
Alex Ant cd86f3c8ea redis auth 2024-09-30 15:15:57 +05:00
Alex Ant 58026ebc2d fix redis auth 2024-09-30 15:07:33 +05:00
Alex Ant 9183275dad redis authentification 2024-09-30 15:00:38 +05:00
Alex Ant 5e3a625d95 chore(release): publish 2024-09-30 14:52:28 +05:00
Alex Ant 3297f9d2d2 update package.json 2024-09-30 14:51:18 +05:00
Alex Ant 29b8306a28 chore(release): publish 2024-09-29 19:17:36 +05:00
Alex Ant d84746bac6 add compression package 2024-09-29 19:14:12 +05:00
Alex Ant 4eacf2ff0b chore(release): publish 2024-09-29 19:01:29 +05:00
Alex Ant a68e0d6f61 update 2024-09-29 18:57:09 +05:00
Alex Ant ddf44304c7 order_id -> order_num, stable initial_order 2024-09-29 15:28:16 +05:00
Alex Ant 789d98f58e chore(release): publish 2024-09-29 09:39:57 +05:00
Alex Ant 205574620d Merge branch 'testnet' 2024-09-29 09:39:19 +05:00
Alex Ant d9bae12b31 chore(release): publish 2024-09-29 09:36:26 +05:00
Alex Ant c951190794 update 2024-09-29 09:34:32 +05:00
Alex Ant d4e1d69c3c update 2024-09-29 09:29:53 +05:00
Alex Ant f93a32c07b update 2024-09-29 09:25:10 +05:00
Alex Ant 8e7c152c0d update 2024-09-29 09:23:20 +05:00
Alex Ant 6a64404f20 update 2024-09-29 09:19:43 +05:00
Alex Ant 1a09589add from-packages 2024-09-29 09:18:03 +05:00
Alex Ant d0f9072ab5 fixed packet version 2024-09-29 09:15:58 +05:00
Alex Ant 011ed9f2d8 update 2024-09-29 09:11:57 +05:00
Alex Ant 12332f83d9 Merge branch 'dev' into testnet 2024-09-29 09:05:09 +05:00
Alex Ant 8f75829948 update 2024-09-29 09:04:53 +05:00
Alex Ant a7ffedb3b2 update 2024-09-29 09:03:14 +05:00
Alex Ant 378d3b9747 update 2024-09-29 09:02:06 +05:00
Alex Ant 5ba05409c4 chore(release): publish
- coopback@1.7.38-alpha.3
 - coopdoc-generator-ts@1.0.21-alpha.3
 - cooptypes@1.0.26-alpha.3
 - coop-notificator@0.0.29-alpha.3
 - terminal@0.1.51-alpha.3
2024-09-29 08:58:35 +05:00
Alex Ant d86beef58f document updates 2024-09-29 08:57:37 +05:00
Alex Ant 7315d67c9f chore(release): publish
- coopback@1.7.38-alpha.2
 - coopdoc-generator-ts@1.0.21-alpha.2
 - cooptypes@1.0.26-alpha.2
 - coop-notificator@0.0.29-alpha.2
 - terminal@0.1.51-alpha.2
2024-09-28 19:43:01 +05:00
Alex Ant 59d79b8c7a update order statuses, list order statuses, add passport data, update registry documents 2024-09-28 19:41:12 +05:00
Alex Ant 3df97653a2 TSK-181 StatusPage and setStatus for orders [pre] 2024-09-26 21:30:08 +05:00
Alex Ant 948d55e418 download qr and show order data 2024-09-23 21:18:10 +05:00
Alex Ant 1d2c7281b1 sberbankPollingProvider prototype 2024-09-23 12:46:12 +05:00
Alex Ant 35759b943c chore(release): publish
- coopback@1.7.38-alpha.1
 - coopdoc-generator-ts@1.0.21-alpha.1
 - cooptypes@1.0.26-alpha.1
 - coop-notificator@0.0.29-alpha.1
 - terminal@0.1.51-alpha.1
2024-09-20 12:13:47 +05:00
Alex Ant 29da33e200 update 2024-09-20 12:12:06 +05:00
Alex Ant 1d758f8126 gitignore 2024-09-20 10:09:54 +05:00
Alex Ant b663dac2ab delete logs 2024-09-20 10:09:32 +05:00
Alex Ant 485a3971e9 update 2024-09-20 10:09:13 +05:00
Alex Ant 36b5d64ca6 chore(release): publish
- coopback@1.7.38-alpha.0
 - coopdoc-generator-ts@1.0.21-alpha.0
 - cooptypes@1.0.26-alpha.0
 - coop-notificator@0.0.29-alpha.0
 - terminal@0.1.51-alpha.0
2024-09-16 12:14:29 +05:00
Alex Ant 8462a709bc hz 2024-09-16 12:13:44 +05:00
Alex Ant 20cabe8362 update 2024-09-16 12:00:54 +05:00
Alex Ant 6967864361 chore(release): publish
- coopback@1.7.37-alpha.3
 - coopdoc-generator-ts@1.0.11-alpha.2
 - terminal@0.1.41-alpha.2
2024-09-16 11:58:50 +05:00
Alex Ant a6ee3840ae update 2024-09-16 11:57:43 +05:00
Alex Ant 01de6139df update 2024-09-16 11:46:48 +05:00
Alex Ant 6ba0924f6c chore(release): publish
- coopback@1.7.37-alpha.2
 - coopdoc-generator-ts@1.0.11-alpha.2
 - cooptypes@1.0.22-alpha.6
 - coop-notificator@0.0.28-alpha.1
 - terminal@0.1.41-alpha.1
2024-09-16 11:44:22 +05:00
Alex Ant 00c75d1fd8 update 2024-09-16 11:43:37 +05:00
Alex Ant 93f28fa9d5 update 2024-09-16 11:38:25 +05:00
Alex Ant 0aed10eb8b chore(release): publish
- coopback@1.7.37-alpha.1
 - coopdoc-generator-ts@1.0.11-alpha.1
 - cooptypes@1.0.22-alpha.6
 - coop-notificator@0.0.28-alpha.0
 - terminal@0.1.41-alpha.0
2024-09-16 11:37:13 +05:00
Alex Ant d84d687eee update 2024-09-16 11:36:50 +05:00
Alex Ant d046f56832 update 2024-09-16 11:34:07 +05:00
Alex Ant 0af1fbf313 update 2024-09-16 11:24:50 +05:00
Alex Ant e9aaf4309e chore(release): publish
- cooparser-ts@1.0.20-alpha.0
 - coopback@1.7.37-alpha.0
 - coopdoc-generator-ts@1.0.11-alpha.0
 - cooptypes@1.0.22-alpha.6
 - coop-notificator@0.0.27
 - terminal@0.1.40
2024-09-16 11:19:45 +05:00
Alex Ant 80fa1085d2 FUCK 2024-09-16 11:13:22 +05:00
Alex Ant 88195291fd update 2024-09-16 11:09:40 +05:00
Alex Ant 39ad600d00 update 2024-09-16 10:58:59 +05:00
Alex Ant c63a3aba6b update 2024-09-16 10:41:15 +05:00
Alex Ant 782ecbe307 dfdf 2024-09-16 10:36:54 +05:00
Alex Ant f75bbfa048 fix 2024-09-16 10:15:16 +05:00
Alex Ant 3a772cc983 herna 2024-09-16 10:00:29 +05:00
Alex Ant 807113523e documents update 2024-09-16 09:52:00 +05:00
Alex Ant 7df2af8611 update 2024-09-15 17:28:33 +05:00
Alex Ant 10c1697b00 update 2024-09-15 17:23:58 +05:00
Alex Ant 742e5d38ab chore(release): publish
- coopback@1.7.35-alpha.5
 - coopdoc-generator-ts@1.0.79-alpha.5
 - cooptypes@1.0.22-alpha.5
 - coop-notificator@0.0.26-alpha.5
 - terminal@0.1.39-alpha.5
2024-09-15 17:20:44 +05:00
Alex Ant 1d3e7f8af0 update 2024-09-15 17:19:13 +05:00
Alex Ant c99bacab64 before update 2024-09-15 10:40:18 +05:00
Alex Ant 95d7555ebc ssr & covars -> vars 2024-09-15 09:38:02 +05:00
Alex Ant 5854e0a23c chore(release): publish
- coopback@1.7.35-alpha.4
 - coopdoc-generator-ts@1.0.79-alpha.4
 - cooptypes@1.0.22-alpha.4
 - coop-notificator@0.0.26-alpha.4
 - terminal@0.1.39-alpha.4
2024-09-14 17:02:55 +05:00
Alex Ant 81f7f32767 fix 2024-09-14 17:02:33 +05:00
Alex Ant c0374a7da1 chore(release): publish
- coopback@1.7.35-alpha.3
 - coopdoc-generator-ts@1.0.79-alpha.3
 - cooptypes@1.0.22-alpha.3
 - coop-notificator@0.0.26-alpha.3
 - terminal@0.1.39-alpha.3
2024-09-14 16:44:32 +05:00
Alex Ant ed65e655b9 update 2024-09-14 16:43:06 +05:00
Alex Ant d250e516b5 update document models 2024-09-14 12:43:06 +05:00
Alex Ant e4f404b2c7 documents update 2024-09-13 20:41:00 +05:00
Alex Ant 86571331f8 update registry 2024-09-12 15:05:11 +05:00
Alex Ant 163d420af9 request agreements 2024-09-11 16:12:05 +05:00
Alex Ant 4925ea4af0 chore(release): publish
- cooparser-ts@1.0.19-alpha.1
 - coopback@1.7.35-alpha.2
 - coopdoc-generator-ts@1.0.79-alpha.2
 - cooptypes@1.0.22-alpha.2
 - coop-notificator@0.0.26-alpha.2
 - terminal@0.1.39-alpha.2
2024-09-11 10:04:46 +05:00
Alex Ant 57b05ce348 registration agreements 2024-09-11 10:01:09 +05:00
Alex Ant 427b53fcbd chore(release): publish
- coopback@1.7.35-alpha.1
 - coopdoc-generator-ts@1.0.79-alpha.1
 - cooptypes@1.0.22-alpha.1
 - coop-notificator@0.0.26-alpha.1
 - terminal@0.1.39-alpha.1
2024-09-10 10:06:12 +05:00
Alex Ant 2ac7a31be6 промежуточный результат добавления кооперативных соглашений 2024-09-10 10:05:17 +05:00
Alex Ant 4baed6409f chore(release): publish
- cooparser-ts@1.0.19-alpha.0
 - coopback@1.7.35-alpha.0
 - coopdoc-generator-ts@1.0.79-alpha.0
 - cooptypes@1.0.22-alpha.0
 - coop-notificator@0.0.26-alpha.0
 - terminal@0.1.39-alpha.0
2024-09-06 16:39:34 +05:00
Alex Ant 2ea0ff0965 big update 2024-09-06 16:29:18 +05:00
Alex Ant 88b9a7edce small letters 2024-09-05 19:27:23 +05:00
Alex Ant 538066b960 ufff template or Template ??? always should be small letters 2024-09-05 19:25:37 +05:00
Alex Ant b10dd1d75a update generator with new type of document 2024-09-04 20:57:59 +05:00
Alex Ant f743580b55 fix signature collection name 2024-09-03 20:33:30 +05:00
Alex Ant 0688467302 update 2024-09-03 20:11:17 +05:00
Alex Ant 29e972dbf2 fix is_paid 2024-08-27 18:47:39 +05:00
Alex Ant bd99697c5b chore(release): publish
- coopback@1.7.34
 - coopdoc-generator-ts@1.0.78
 - cooptypes@1.0.21
 - coop-notificator@0.0.25
 - terminal@0.1.38
2024-08-25 11:39:35 +05:00
Alex Ant 1d5c431ff6 update types 2024-08-25 11:38:40 +05:00
Alex Ant 3736c510ff chore(release): publish
- cooparser-ts@1.0.18
 - coopback@1.7.33
 - coopdoc-generator-ts@1.0.77
 - terminal@0.1.37
2024-08-25 11:27:44 +05:00
Alex Ant 26c12c3a85 update 2024-08-25 11:25:28 +05:00
Alex Ant 10bb08e5e6 chore(release): publish
- coopback@1.7.32
 - coopdoc-generator-ts@1.0.76
 - terminal@0.1.36
2024-08-25 11:19:13 +05:00
Alex Ant b50d5b6121 publish 2024-08-25 11:07:57 +05:00
Alex Ant 38b28752e1 chore(release): publish
- coopback@1.7.31
 - coopdoc-generator-ts@1.0.75
 - cooptypes@1.0.20
 - coop-notificator@0.0.24
 - terminal@0.1.35
2024-08-25 11:02:44 +05:00
Alex Ant 87c51009de ProgramProvision | ЦПП Цифровой Кошелёк 2024-08-25 10:59:57 +05:00
Alex Ant a950a47b28 chore(release): publish
- coopback@1.7.31-alpha.1
 - coopdoc-generator-ts@1.0.75-alpha.1
 - cooptypes@1.0.20-alpha.1
 - coop-notificator@0.0.24-alpha.1
 - terminal@0.1.35-alpha.1
2024-08-23 10:38:04 +05:00
Alex Ant 2609d10c0b update 2024-08-23 10:35:48 +05:00
Alex Ant 7b4cb0f66c publish 2024-08-23 10:34:38 +05:00
Alex Ant 26db0e1e69 push 2024-08-21 15:57:02 +05:00
Alex Ant 62e64cbd22 upgrade 2024-08-21 14:43:43 +05:00
Alex Ant 844a47830f fix types 2024-08-21 13:11:37 +05:00
Alex Ant 2cc1e32f45 chore(release): publish
- coopback@1.7.31-alpha.0
 - coopdoc-generator-ts@1.0.75-alpha.0
 - cooptypes@1.0.20-alpha.0
 - coop-notificator@0.0.24-alpha.0
 - terminal@0.1.35-alpha.0
2024-08-21 12:53:38 +05:00
Alex Ant 9890958b1e update contracts interface 2024-08-21 12:50:44 +05:00
Alex Ant 6dbd6d6edc fix 2024-08-19 14:31:01 +05:00
Alex Ant bf7a4dfd28 путь установки 2024-08-19 14:20:38 +05:00
Alex Ant f52626bda0 Полное разделение форм ввода данных пользователя пригодное для использования в процессе инсталляции 2024-08-16 16:17:24 +05:00
Alex Ant 88cec4bf2b рефакторинг | вынос форм для ввода пользовательской информации в shared для дальнейшего использования в модуле установки 2024-08-15 20:30:01 +05:00
Alex Ant b880def108 fix 2024-08-15 12:39:19 +05:00
Alex Ant bfd5dc039a addUser в панели управления 2024-08-15 12:28:18 +05:00
Alex Ant c0d236dff3 chore(release): publish
- coopback@1.7.30
 - coopdoc-generator-ts@1.0.74
 - cooptypes@1.0.19
 - coop-notificator@0.0.23
 - terminal@0.1.34
2024-08-13 23:03:13 +05:00
Alex Ant 743d5fc306 разделение формы для ввода персональных данных с регистратором; зародыш формы добавления пайщика в реестр. 2024-08-13 23:00:09 +05:00
Alex Ant 2f51516163 step to install | works on add user by api 2024-08-13 15:21:23 +05:00
Alex Ant b606b46aa4 страница настроек с кнопками выхода для пайщика 2024-08-05 14:31:27 +05:00
Alex Ant 5b65ff99a0 chore(release): publish
- coopback@1.7.29
 - coopdoc-generator-ts@1.0.73
 - cooptypes@1.0.18
 - coop-notificator@0.0.22
 - terminal@0.1.33
2024-08-05 12:36:01 +05:00
Alex Ant 74a3f52324 update 2024-08-05 12:32:23 +05:00
Alex Ant 7c2a4fdfa8 удаление потерявшейся папки 2024-08-05 12:05:05 +05:00
Alex Ant fecee3a098 fix naming 2024-08-05 11:56:29 +05:00
Alex Ant 45f7111fb9 chore(release): publish
- coopback@1.7.29-alpha.0
 - coopdoc-generator-ts@1.0.73-alpha.0
 - cooptypes@1.0.18-alpha.0
 - coop-notificator@0.0.22-alpha.0
 - terminal@0.1.33-alpha.0
2024-08-05 11:51:37 +05:00
Alex Ant f2e23a8062 перевыпуск ключа доступа 2024-08-05 11:38:10 +05:00
Alex Ant 36a3631f5e login with signature 2024-08-02 17:11:01 +05:00
Alex Ant a758d19a9f обновление mongoose, интеграция eslint и активация typescript проверок 2024-08-01 14:06:01 +05:00
Alex Ant aac3e53a30 eslint repair 2024-08-01 13:06:28 +05:00
Alex Ant 85d87ee210 FIX !!! 2024-07-31 20:48:38 +05:00
Alex Ant 2f3ee80ed4 Merge branch 'main' into dev 2024-07-31 17:26:20 +05:00
Alex Ant 3632bea54e chore(release): publish
- terminal@0.1.32
2024-07-31 17:26:08 +05:00
Alex Ant 4a0521751a update 2024-07-31 17:24:44 +05:00
Alex Ant 7d6266c241 chore(release): publish
- terminal@0.1.32-alpha.0
2024-07-31 16:28:53 +05:00
Alex Ant 1d69b9ffea Рабочие столы v1 2024-07-31 16:24:50 +05:00
Alex Ant 72674cba10 chore(release): publish
- coopback@1.7.28
 - terminal@0.1.31
2024-07-26 18:42:47 +05:00
Alex Ant 495a8e2d1e chore(release): publish
- coopback@1.7.28-alpha.0
 - terminal@0.1.31-alpha.0
2024-07-26 18:41:33 +05:00
Alex Ant 95ae221d60 Добавление платежных реквизитов | удаление | просмотр | свайп в рамках страницы 2024-07-26 18:38:14 +05:00
Alex Ant 857f746da1 bug fix 2024-07-26 11:03:52 +05:00
Alex Ant 0e2e3052b1 works 2024-07-25 21:00:04 +05:00
Alex Ant 167c04cc3f commit 2024-07-25 20:47:42 +05:00
Alex Ant 043f51479a looking for bug #2 2024-07-25 20:30:56 +05:00
Alex Ant 921282df81 looking for bug 2024-07-25 20:20:44 +05:00
Alex Ant b3c641501c migration 2024-07-25 20:07:44 +05:00
Alex Ant 3608e7601f chore(release): publish
- cooparser-ts@1.0.17
 - coopback@1.7.27
 - coopdoc-generator-ts@1.0.72
 - cooptypes@1.0.17
 - coop-notificator@0.0.21
 - terminal@0.1.30
2024-07-25 19:41:18 +05:00
Alex Ant a75cfa1056 chore(release): publish
- coopback@1.7.27-alpha.5
 - terminal@0.1.30-alpha.4
2024-07-25 19:39:41 +05:00
Alex Ant f08c4102fd login with email 2024-07-25 19:37:13 +05:00
Alex Ant 9bfd7c7d9a chore(release): publish
- coopback@1.7.27-alpha.4
2024-07-25 18:24:15 +05:00
Alex Ant a359b4fbdb fix 2024-07-25 18:22:17 +05:00
Alex Ant effb6df495 chore(release): publish
- cooparser-ts@1.0.17-alpha.2
 - coopback@1.7.27-alpha.3
 - coopdoc-generator-ts@1.0.72-alpha.3
 - cooptypes@1.0.17-alpha.3
 - coop-notificator@0.0.21-alpha.3
 - terminal@0.1.30-alpha.3
2024-07-25 17:56:22 +05:00
Alex Ant 6e6c963663 update 2024-07-25 17:55:36 +05:00
Alex Ant 23f5c7b578 update 2024-07-25 17:55:14 +05:00
Alex Ant 02b223266d pre 2024-07-25 17:05:44 +05:00
Alex Ant 745a8c99e1 publish cooptypes 2024-07-25 17:03:17 +05:00
Alex Ant 5532038fd8 coopback payment methods (list | add | del) & tests 2024-07-25 16:06:06 +05:00
Alex Ant 3be31c5240 coopback tests work 2024-07-24 23:30:01 +05:00
Alex Ant 11ab59e109 coopback tests restore #1 2024-07-23 22:34:42 +05:00
Alex Ant d5bbf10041 before generator refactoring 2024-07-23 10:10:22 +05:00
Alex Ant ba4f9581a4 before generator refactoring 2024-07-23 09:46:19 +05:00
Alex Ant 52eabab633 chore(release): publish
- coopback@1.7.27-alpha.0
 - coopdoc-generator-ts@1.0.72-alpha.0
 - cooptypes@1.0.17-alpha.0
 - coop-notificator@0.0.21-alpha.0
 - terminal@0.1.30-alpha.0
2024-07-18 20:15:52 +05:00
Alex Ant 600949b784 изменяемые публичные контакты кооператива 2024-07-18 20:09:46 +05:00
Alex Ant dcca48097d chore(members): убран лишний код 2024-07-16 21:21:06 +05:00
Alex Ant 6e20c32a14 update 2024-07-16 21:13:51 +05:00
Alex Ant 0cd1af0cf1 chore(release): publish
- cooparser-ts@1.0.16
 - coopback@1.7.26
 - coopdoc-generator-ts@1.0.71
 - cooptypes@1.0.16
 - coop-notificator@0.0.20
 - terminal@0.1.29
2024-07-15 18:51:34 +05:00
Alex Ant d786dbc095 chore(release): publish
- coop-notificator@0.0.20-alpha.1
2024-07-15 18:36:08 +05:00
Alex Ant 5b0581158a fix тип socketio 2024-07-15 18:30:36 +05:00
Alex Ant dced33c8e6 chore(release): publish
- cooparser-ts@1.0.16-alpha.0
 - coopback@1.7.26-alpha.0
 - coopdoc-generator-ts@1.0.71-alpha.0
 - cooptypes@1.0.16-alpha.0
 - coop-notificator@0.0.20-alpha.0
 - terminal@0.1.29-alpha.1
2024-07-15 17:44:30 +05:00
Alex Ant 1a9ab8d997 1. Введен WS-нотификатор, отправляющий анонимизированные оповещения всем подписанантам
2. Контроллер подключен к нотификатору для циркулярного обновления прав доступа членов совета
3. Введены настройки кооператива: управление советом и просмотр реквизитов.
2024-07-15 17:41:03 +05:00
Alex Ant 0f4da3ad18 chore(release): publish
- terminal@0.1.29-alpha.0
2024-07-14 14:31:43 +05:00
Alex Ant bba8a72eef update 2024-07-14 14:30:22 +05:00
Alex Ant 7f0a81a1bc chore(release): publish
- terminal@0.1.28
2024-07-14 14:18:54 +05:00
Alex Ant 38db03b4fc chore(release): publish
- terminal@0.1.28-alpha.0
2024-07-14 14:17:57 +05:00
Alex Ant 409ba6c104 update 2024-07-14 14:17:29 +05:00
Alex Ant e9c11a0866 chore(release): publish
- terminal@0.1.27
2024-07-14 13:01:51 +05:00
Alex Ant 8d3bf8c5b6 chore(release): publish
- terminal@0.1.27-alpha.0
2024-07-14 12:59:59 +05:00
Alex Ant 00d46e4b3a update 2024-07-14 12:57:01 +05:00
Alex Ant df94c7f30a chore(release): publish
- cooparser-ts@1.0.15
 - coopback@1.7.25
 - coopdoc-generator-ts@1.0.70
 - cooptypes@1.0.15
 - coop-notificator@0.0.19
 - terminal@0.1.26
2024-07-14 10:23:35 +05:00
Alex Ant e2469f8cfb update 2024-07-14 10:19:56 +05:00
Alex Ant 9f1bb73326 chore(release): publish
- cooparser-ts@1.0.15-alpha.0
 - coopback@1.7.25-alpha.0
 - coopdoc-generator-ts@1.0.70-alpha.0
 - cooptypes@1.0.15-alpha.0
 - coop-notificator@0.0.19-alpha.0
 - terminal@0.1.26-alpha.0
2024-07-14 10:13:58 +05:00
Alex Ant c683a83f78 исправлена проблема контроля доступа к страницам, когда доступ запрещается при первой
загрузке, даже если он есть.
2024-07-14 10:09:33 +05:00
Alex Ant 52c2131cc9 chore(release): publish
- cooparser-ts@1.0.14
 - coopback@1.7.24
 - coopdoc-generator-ts@1.0.69
 - cooptypes@1.0.14
 - coop-notificator@0.0.18
 - terminal@0.1.25
2024-07-13 16:16:25 +05:00
Alex Ant c1a8603a1c chore(release): publish
- cooparser-ts@1.0.14-alpha.0
 - coopback@1.7.24-alpha.0
 - coopdoc-generator-ts@1.0.69-alpha.0
 - cooptypes@1.0.14-alpha.0
 - coop-notificator@0.0.18-alpha.0
 - terminal@0.1.25-alpha.0
2024-07-13 16:11:47 +05:00
Alex Ant 6e766154a7 Merge branch 'dev' into testnet 2024-07-13 16:10:38 +05:00
Alex Ant 53b56867c7 nothing 2024-07-13 16:10:18 +05:00
Alex Ant a8d0079608 Merge branch 'main' into dev 2024-07-13 16:09:43 +05:00
Alex Ant 515603ceab Merge branch 'dev' into testnet 2024-07-13 16:07:59 +05:00
Alex Ant 3587a1158d nothing 2024-07-13 16:07:48 +05:00
Alex Ant 166a2411b5 chore(release): publish
- coopback@1.7.23
2024-07-13 16:05:45 +05:00
Alex Ant 101dc23132 chore(release): publish
- coopback@1.7.22
2024-07-13 16:04:32 +05:00
Alex Ant a941a2d090 Merge branch 'testnet' 2024-07-13 16:02:53 +05:00
Alex Ant 2fa320e1ce chore(release): publish
- coopback@1.7.22-alpha.3
2024-07-13 15:52:54 +05:00
Alex Ant f667b342a7 Merge branch 'dev' into testnet 2024-07-13 15:51:47 +05:00
Alex Ant 4a89b28aab nothing 2024-07-13 15:50:11 +05:00
Alex Ant ef49226014 chore(release): publish
- cooparser-ts@1.0.13
 - coopback@1.7.22
 - coopdoc-generator-ts@1.0.68
 - cooptypes@1.0.13
 - coop-notificator@0.0.17
 - terminal@0.1.24
2024-07-13 15:46:39 +05:00
Alex Ant 6a1616514b nothing 2024-07-13 15:43:31 +05:00
Alex Ant 3bc9b29374 chore(release): publish
- cooparser-ts@1.0.13-alpha.0
 - coopback@1.7.22-alpha.2
 - coopdoc-generator-ts@1.0.68-alpha.1
 - coop-notificator@0.0.17-alpha.1
2024-07-13 15:40:31 +05:00
Alex Ant 8036906c49 Merge branch 'dev' into testnet 2024-07-13 15:39:28 +05:00
Alex Ant 96ca153fb1 nothing 2024-07-13 15:38:51 +05:00
Alex Ant c25be00f5e Merge branch 'dev' into testnet 2024-07-13 13:27:15 +05:00
Alex Ant 17d1e878a5 docker 2024-07-13 13:27:04 +05:00
Alex Ant 3cb3dca852 chore(release): publish
- coopback@1.7.22-alpha.1
2024-07-13 13:18:48 +05:00
Alex Ant c23ae9e959 Merge branch 'dev' into testnet 2024-07-13 13:18:06 +05:00
Alex Ant 758ae249f5 nothing 2024-07-13 13:17:30 +05:00
Alex Ant b4dab27214 chore(release): publish
- coopback@1.7.22-alpha.0
 - coopdoc-generator-ts@1.0.68-alpha.0
 - cooptypes@1.0.13-alpha.0
 - coop-notificator@0.0.17-alpha.0
 - terminal@0.1.23-alpha.1
2024-07-13 13:14:15 +05:00
Alex Ant 8fb6524414 Merge branch 'dev' into testnet 2024-07-13 13:13:35 +05:00
Alex Ant 9a9034f28a nothing 2024-07-13 13:06:51 +05:00
Alex Ant b92478c0a2 chore(release): publish
- terminal@0.1.23
2024-07-13 13:02:02 +05:00
Alex Ant 595e39c0f0 Merge branch 'testnet' 2024-07-13 13:01:28 +05:00
Alex Ant 22ed4a6a5e chore(release): publish
- terminal@0.1.23-alpha.0
2024-07-13 13:01:10 +05:00
Alex Ant 8a9d6168e3 Merge branch 'dev' into testnet 2024-07-13 13:00:12 +05:00
Alex Ant b8f25734d8 nothing 2024-07-13 12:59:59 +05:00
Alex Ant f3cd93e854 Merge branch 'testnet' 2024-07-13 12:58:46 +05:00
Alex Ant fad4e22e35 chore(release): publish
- terminal@0.1.22
2024-07-13 12:58:39 +05:00
Alex Ant 93abe0aeff chore(release): publish
- terminal@0.1.22-alpha.0
2024-07-13 12:57:43 +05:00
Alex Ant 60bf91e324 Merge branch 'dev' into testnet 2024-07-13 12:57:07 +05:00
Alex Ant 107181a499 nothing 2024-07-13 12:56:55 +05:00
Alex Ant 28ca2758f0 Merge branch 'testnet' 2024-07-13 12:54:40 +05:00
Alex Ant ea35eb09ed chore(release): publish
- terminal@0.1.21
2024-07-13 12:54:33 +05:00
Alex Ant a1ca65f91c chore(release): publish
- terminal@0.1.21-alpha.0
2024-07-13 12:53:23 +05:00
Alex Ant 80c7d5b5de Merge branch 'dev' into testnet 2024-07-13 12:52:54 +05:00
Alex Ant aa48d8e91e nothing 2024-07-13 12:52:43 +05:00
Alex Ant 4e39f53602 Merge branch 'testnet' 2024-07-13 12:52:21 +05:00
Alex Ant 222e4871f8 chore(release): publish
- terminal@0.1.20
2024-07-13 12:51:38 +05:00
Alex Ant 791f818fb3 chore(release): publish
- terminal@0.1.20-alpha.0
2024-07-13 12:50:55 +05:00
Alex Ant 32cbe7b15d Merge branch 'dev' into testnet 2024-07-13 12:50:31 +05:00
Alex Ant 0d0135c54a nothing 2024-07-13 12:50:05 +05:00
Alex Ant 00873c07f2 chore(release): publish
- terminal@0.1.19
2024-07-13 12:49:00 +05:00
Alex Ant 21ace2f27e chore(release): publish
- terminal@0.1.19-alpha.2
2024-07-13 12:48:08 +05:00
Alex Ant 9c1e25959c Merge branch 'dev' into testnet 2024-07-13 12:47:26 +05:00
Alex Ant c9071b55cc nothing 2024-07-13 12:46:54 +05:00
Alex Ant 8c92cc3390 Merge branch 'testnet' 2024-07-13 12:45:06 +05:00
Alex Ant 24a8c5023e chore(release): publish
- terminal@0.1.19-alpha.1
2024-07-13 12:43:31 +05:00
Alex Ant e38c553d1e Merge branch 'dev' into testnet 2024-07-13 12:43:05 +05:00
Alex Ant 7f56aef1fb nothing 2024-07-13 12:42:54 +05:00
Alex Ant 9bc88a8472 chore(release): publish
- terminal@0.1.19-alpha.0
2024-07-13 12:41:51 +05:00
Alex Ant fcf13f0056 Merge branch 'dev' into testnet 2024-07-13 12:41:26 +05:00
Alex Ant faeb1b0048 nothing 2024-07-13 12:41:08 +05:00
Alex Ant 6c7ee68fa9 chore(release): publish
- terminal@0.1.18
2024-07-13 12:37:08 +05:00
Alex Ant 38815b9339 chore(release): publish
- terminal@0.1.17
2024-07-13 12:36:42 +05:00
Alex Ant 734bb9aeef chore(release): publish
- terminal@0.1.16
2024-07-13 12:36:04 +05:00
Alex Ant f021fcc700 chore(release): publish
- terminal@0.1.16-alpha.6
2024-07-13 12:35:03 +05:00
Alex Ant 6727aa275c Merge branch 'dev' into testnet 2024-07-13 12:34:40 +05:00
Alex Ant 680030a16a nothing 2024-07-13 12:34:30 +05:00
Alex Ant 0cf5cdf1f3 chore(release): publish
- terminal@0.1.16-alpha.5
2024-07-13 12:23:19 +05:00
Alex Ant 39c97c7bc6 nothing 2024-07-13 12:22:48 +05:00
Alex Ant bba64ee761 Merge branch 'testnet' 2024-07-13 12:21:51 +05:00
Alex Ant 1fa1fa6eb2 chore(release): publish
- terminal@0.1.16-alpha.4
2024-07-13 12:18:17 +05:00
Alex Ant 946ac9f1df Merge branch 'dev' into testnet 2024-07-13 12:17:53 +05:00
Alex Ant c73e8341c7 nothing 2024-07-13 12:17:45 +05:00
Alex Ant 203e7683f9 Merge branch 'testnet' 2024-07-13 12:15:26 +05:00
Alex Ant b3f9b04cae chore(release): publish
- terminal@0.1.16-alpha.3
2024-07-13 12:12:21 +05:00
Alex Ant 3bdc56690a Merge branch 'dev' into testnet 2024-07-13 12:11:58 +05:00
Alex Ant 20b7298b3e nothing 2024-07-13 12:11:52 +05:00
Alex Ant cd481901c3 nothing 2024-07-13 12:06:21 +05:00
Alex Ant b38c571520 chore(release): publish
- terminal@0.1.16-alpha.2
2024-07-13 12:05:42 +05:00
Alex Ant dfa6f723e4 Merge branch 'dev' into testnet 2024-07-13 12:05:14 +05:00
Alex Ant dae806752d nothing 2024-07-13 12:04:57 +05:00
Alex Ant fa64ce2b10 chore(release): publish
- terminal@0.1.17
2024-07-13 12:04:34 +05:00
Alex Ant f9a0c700a7 Merge branch 'testnet' 2024-07-13 12:04:01 +05:00
Alex Ant ea4b4dd2fd chore(release): publish
- terminal@0.1.16-alpha.1
2024-07-13 12:01:09 +05:00
Alex Ant d1a20ac77d Merge branch 'dev' into testnet 2024-07-13 11:59:28 +05:00
Alex Ant 6fcaa2282d update 2024-07-13 11:59:01 +05:00
Alex Ant afd8e375a2 chore(release): publish [PROD]
- terminal@0.1.16
2024-07-13 11:25:40 +05:00
Alex Ant 852d16d0af update 2024-07-13 11:25:16 +05:00
Alex Ant 64c702b7aa chore(release): publish [TESTNET]
- terminal@0.1.16-alpha.0
2024-07-13 11:19:48 +05:00
Alex Ant d11ce9c23e update 2024-07-13 11:19:22 +05:00
Alex Ant 6db49ea230 update 2024-07-13 11:15:37 +05:00
Alex Ant 6e217c3847 update 2024-07-13 10:56:25 +05:00
Alex Ant 5db6301ed1 update 2024-07-13 10:55:09 +05:00
Alex Ant e1030860c7 update 2024-07-13 10:54:32 +05:00
Alex Ant 2bfd982b35 chore(release): publish [PROD]
- cooparser-ts@1.0.12
 - coopback@1.7.21
 - coopdoc-generator-ts@1.0.67
 - cooptypes@1.0.12
 - coop-notificator@0.0.16
 - terminal@0.1.15
2024-07-13 09:53:29 +05:00
Alex Ant 548da13b32 chore(release): publish [TESTNET]
- cooparser-ts@1.0.12-testnet.1
 - coopback@1.7.21-testnet.1
 - coopdoc-generator-ts@1.0.67-testnet.1
 - cooptypes@1.0.12-testnet.1
 - coop-notificator@0.0.16-testnet.1
 - terminal@0.1.15-testnet.1
2024-07-13 09:42:35 +05:00
Alex Ant 9b79009012 update 2024-07-13 09:41:05 +05:00
Alex Ant 103a900511 Введена раздельная стоимость регистрации для физлиц/ип и организаций 2024-07-12 22:50:26 +05:00
Alex Ant 92b779f8b2 update 2024-07-12 16:48:50 +05:00
Alex Ant 19430db1a6 chore(release): publish [PROD]
- coopback@1.7.20
 - terminal@0.1.14
2024-07-11 20:46:24 +05:00
Alex Ant 869d82a434 chore(release): publish [TESTNET]
- coopback@1.7.20-testnet.0
 - terminal@0.1.14-testnet.0
2024-07-11 20:45:24 +05:00
Alex Ant abe5266e65 update 2024-07-11 20:44:48 +05:00
Alex Ant 073ea67c07 chore(release): publish [PROD]
- coopback@1.7.19
 - coop-notificator@0.0.15
2024-07-11 20:43:57 +05:00
Alex Ant fd378bd52a chore(release): publish [TESTNET]
- coopback@1.7.19-testnet.0
 - coop-notificator@0.0.15-testnet.0
2024-07-11 20:42:51 +05:00
Alex Ant 67b8670d0f update 2024-07-11 20:41:41 +05:00
Alex Ant 82ffdd4820 chore(release): publish [PROD]
- coopback@1.7.18
 - coop-notificator@0.0.14
 - terminal@0.1.13
2024-07-11 20:11:56 +05:00
Alex Ant b96f9e39f1 chore(release): publish [TESTNET]
- coopback@1.7.18-testnet.0
 - coop-notificator@0.0.14-testnet.0
 - terminal@0.1.13-testnet.0
2024-07-11 20:11:04 +05:00
Alex Ant bd24eea5b4 update 2024-07-11 20:10:09 +05:00
Alex Ant bcaab4e7d1 chore(release): publish [PROD]
- coopback@1.7.17
 - coop-notificator@0.0.13
 - terminal@0.1.12
2024-07-11 20:04:21 +05:00
Alex Ant 01f9a90d8a chore(release): publish [TESTNET]
- coopback@1.7.17-testnet.0
 - coop-notificator@0.0.13-testnet.0
 - terminal@0.1.12-testnet.0
2024-07-11 20:02:53 +05:00
Alex Ant 00e0fad9ca update 2024-07-11 20:02:10 +05:00
Alex Ant a677c0e64d chore(release): publish [PROD]
- cooparser-ts@1.0.11
 - coopback@1.7.16
 - coopdoc-generator-ts@1.0.66
 - coop-notificator@0.0.12
 - terminal@0.1.11
2024-07-11 19:59:35 +05:00
Alex Ant 82379d8763 chore(release): publish [TESTNET]
- coopback@1.7.16-testnet.4
2024-07-11 19:58:09 +05:00
Alex Ant 33d9830a75 update 2024-07-11 19:57:29 +05:00
Alex Ant d291603c13 chore(release): publish [TESTNET]
- cooparser-ts@1.0.11-testnet.1
 - coopback@1.7.16-testnet.3
 - coopdoc-generator-ts@1.0.66-testnet.1
 - coop-notificator@0.0.12-testnet.3
 - terminal@0.1.11-testnet.1
2024-07-11 19:36:59 +05:00
Alex Ant e97df22ffd update 2024-07-11 19:35:57 +05:00
Alex Ant 4c33813eb4 chore(release): publish [TESTNET]
- coopback@1.7.16-testnet.2
 - coop-notificator@0.0.12-testnet.2
 - terminal@0.1.11-testnet.0
2024-07-11 19:32:58 +05:00
Alex Ant 5a3c6f0dec update 2024-07-11 19:31:13 +05:00
Alex Ant 6811c456b4 chore(release): publish [TESTNET]
- coopback@1.7.16-testnet.1
 - coop-notificator@0.0.12-testnet.1
2024-07-11 19:30:17 +05:00
Alex Ant 25c705888b update 2024-07-11 19:29:27 +05:00
Alex Ant 911ce4ca10 chore(release): publish [TESTNET]
- cooparser-ts@1.0.11-testnet.0
 - coopback@1.7.16-testnet.0
 - coopdoc-generator-ts@1.0.66-testnet.0
 - coop-notificator@0.0.12-testnet.0
2024-07-11 19:26:08 +05:00
Alex Ant 4be30763c8 update 2024-07-11 19:24:42 +05:00
Alex Ant 38e6f5e0b0 chore(release): publish [PROD]
- cooparser-ts@1.0.10
 - coopback@1.7.15
 - coopdoc-generator-ts@1.0.65
 - coop-notificator@0.0.11
 - terminal@0.1.10
2024-07-11 19:23:29 +05:00
Alex Ant 8f63f6990c chore(release): publish [TESTNET]
- cooparser-ts@1.0.10-testnet.0
 - coopback@1.7.15-testnet.0
 - coopdoc-generator-ts@1.0.65-testnet.0
 - coop-notificator@0.0.11-testnet.0
 - terminal@0.1.10-testnet.1
2024-07-11 19:21:13 +05:00
Alex Ant 01af445256 update 2024-07-11 19:18:39 +05:00
Alex Ant a857b50435 chore(release): publish [TESTNET]
- terminal@0.1.10-testnet.0
2024-07-11 19:10:14 +05:00
Alex Ant 8a3c0b3f5d update 2024-07-11 19:09:50 +05:00
Alex Ant d7ad724f15 chore(release): publish [PROD]
- cooparser-ts@1.0.9
 - coopback@1.7.14
 - coopdoc-generator-ts@1.0.64
 - coop-notificator@0.0.10
 - terminal@0.1.9
2024-07-11 19:08:10 +05:00
Alex Ant 6b4fa0b6c4 chore(release): publish [TESTNET]
- cooparser-ts@1.0.9-testnet.0
 - coopback@1.7.14-testnet.0
 - coopdoc-generator-ts@1.0.64-testnet.0
 - coop-notificator@0.0.10-testnet.0
 - terminal@0.1.9-testnet.0
2024-07-11 19:04:02 +05:00
Alex Ant ba33176be7 update 2024-07-11 19:02:36 +05:00
Alex Ant 63ff87ff71 chore(release): publish [PROD]
- cooparser-ts@1.0.8
 - coopback@1.7.13
 - coopdoc-generator-ts@1.0.63
2024-07-11 18:50:10 +05:00
Alex Ant 06a8ffb065 chore(release): publish [TESTNET]
- cooparser-ts@1.0.8-testnet.2
 - coopback@1.7.13-testnet.2
 - coopdoc-generator-ts@1.0.63-testnet.2
2024-07-11 18:40:04 +05:00
Alex Ant b9565f72ea update 2024-07-11 18:38:57 +05:00
Alex Ant f7c1686c54 chore(release): publish [TESTNET]
- cooparser-ts@1.0.8-testnet.1
 - coopback@1.7.13-testnet.1
 - coopdoc-generator-ts@1.0.63-testnet.1
2024-07-11 18:30:54 +05:00
Alex Ant a38773f878 update 2024-07-11 18:30:11 +05:00
Alex Ant 57f93d3ab5 chore(release): publish [TESTNET]
- cooparser-ts@1.0.8-testnet.0
 - coopback@1.7.13-testnet.0
 - coopdoc-generator-ts@1.0.63-testnet.0
2024-07-11 18:25:54 +05:00
Alex Ant 5fac745755 update 2024-07-11 18:24:17 +05:00
Alex Ant dfc64ec00f chore(release): publish [PROD]
- coopback@1.7.12
2024-07-11 18:14:37 +05:00
Alex Ant 3d2b6f1a6a chore(release): publish [TESTNET]
- coopback@1.7.12-testnet.0
2024-07-11 16:52:38 +05:00
Alex Ant 2b459159d2 nothing 2024-07-11 16:51:40 +05:00
Alex Ant 4973277b5e chore(release): publish [PROD]
- coopback@1.7.11
 - coop-notificator@0.0.9
2024-07-11 16:21:02 +05:00
Alex Ant 6ee7d000b2 chore(release): publish [TESTNET]
- coopback@1.7.11-testnet.0
 - coop-notificator@0.0.9-testnet.0
2024-07-11 16:09:31 +05:00
Alex Ant cea38976a2 update 2024-07-11 16:08:55 +05:00
Alex Ant 1a5c8e5600 update 2024-07-11 16:05:31 +05:00
Alex Ant 6e0d76f945 chore(release): publish [PROD]
- coopback@1.7.10
 - coopdoc-generator-ts@1.0.62
 - coop-notificator@0.0.8
2024-07-11 15:50:09 +05:00
Alex Ant 51a4984811 chore(release): publish [TESTNET]
- coop-notificator@0.0.8-testnet.6
2024-07-11 15:48:27 +05:00
Alex Ant fc164fbbaf update 2024-07-11 15:47:22 +05:00
Alex Ant ea889a8286 chore(release): publish [TESTNET]
- coopback@1.7.10-testnet.0
 - coopdoc-generator-ts@1.0.62-testnet.0
 - coop-notificator@0.0.8-testnet.5
2024-07-11 15:42:47 +05:00
Alex Ant 7bb4dd7eec update 2024-07-11 15:33:17 +05:00
Alex Ant 5a8569df5c update 2024-07-11 15:27:00 +05:00
Alex Ant 952549a86d update 2024-07-11 15:19:41 +05:00
Alex Ant 52c2ae607f update 2024-07-11 15:05:51 +05:00
Alex Ant 2c7dfd55b2 up 2024-07-11 15:01:20 +05:00
Alex Ant 6a46697c9d feat: добавлен docker-compose.yaml 2024-07-11 13:04:09 +05:00
Alex Ant 10cf5a0855 chore(release): publish [TESTNET]
- coop-notificator@0.0.8-testnet.4
2024-07-11 12:48:54 +05:00
Alex Ant 1e54729de2 nothing 2024-07-11 12:47:36 +05:00
Alex Ant 073d7832cd chore(release): publish [TESTNET]
- coop-notificator@0.0.8-testnet.3
2024-07-11 12:38:17 +05:00
Alex Ant 1b48c0c7d8 nothing 2024-07-11 12:35:40 +05:00
Alex Ant cd57f02fe0 chore(release): publish [TESTNET]
- coop-notificator@0.0.8-testnet.2
2024-07-11 12:19:49 +05:00
Alex Ant 8485103b70 nothing 2024-07-11 12:16:43 +05:00
Alex Ant 6952d637ad chore(release): publish [TESTNET]
- coop-notificator@0.0.8-testnet.1
2024-07-11 12:07:19 +05:00
Alex Ant 9e5a5c5407 lock 2024-07-11 12:06:23 +05:00
Alex Ant 1ebe0c101c chore(release): publish [TESTNET]
- coop-notificator@0.0.8-testnet.0
2024-07-11 12:04:10 +05:00
Alex Ant 6b19a06d02 nothing 2024-07-11 12:03:14 +05:00
Alex Ant 380dc1ac7b chore(release): publish [PROD]
- coopback@1.7.9
 - coopdoc-generator-ts@1.0.61
 - terminal@0.1.8
2024-07-11 10:33:47 +05:00
Alex Ant 902e28206c chore(release): publish [TESTNET]
- coopback@1.7.9-testnet.0
 - coopdoc-generator-ts@1.0.61-testnet.0
 - terminal@0.1.8-testnet.0
2024-07-10 20:13:39 +05:00
Alex Ant bf89032d8f fix(importers): исправлена ошибка в импорте модуля @wharfkit/contract 2024-07-10 20:11:26 +05:00
Alex Ant aa9f93c03d update 2024-07-10 19:52:59 +05:00
Alex Ant 82df562382 update 2024-07-10 19:49:24 +05:00
Alex Ant 8b66e58a4c update 2024-07-10 19:24:08 +05:00
Alex Ant 7498aeb41c update 2024-07-10 19:19:20 +05:00
Alex Ant 2affcca08c update 2024-07-10 19:14:36 +05:00
Alex Ant 167f81abce chore(release): publish [PROD]
- terminal@0.1.7
2024-07-10 15:39:05 +05:00
Alex Ant dee22f4590 chore(release): publish [TESTNET]
- terminal@0.1.7-testnet.0
2024-07-10 15:38:25 +05:00
Alex Ant 90c6a06084 nothing 2024-07-10 15:38:07 +05:00
Alex Ant ad8d7ef17a chore(release): publish [PROD]
- terminal@0.1.6
2024-07-10 15:35:35 +05:00
Alex Ant cbb662c438 chore(release): publish [TESTNET]
- terminal@0.1.6-testnet.0
2024-07-10 15:32:53 +05:00
Alex Ant 43c3336eff nothing 2024-07-10 15:32:25 +05:00
Alex Ant 19bcfd0fd4 chore(release): publish [PROD]
- terminal@0.1.5
2024-07-10 15:29:51 +05:00
Alex Ant 1bc285ae4a chore(release): publish [TESTNET]
- terminal@0.1.5-testnet.0
2024-07-10 15:29:19 +05:00
Alex Ant ec56bc5fb8 nothing 2024-07-10 15:28:57 +05:00
Alex Ant 8f738b4b03 chore(release): publish [PROD]
- terminal@0.1.4
2024-07-10 15:27:09 +05:00
Alex Ant 39ace62ca9 chore(release): publish [TESTNET]
- terminal@0.1.4-testnet.0
2024-07-10 15:23:20 +05:00
Alex Ant 889447a93c fix(terminal): исправлен шрифт в README 2024-07-10 15:22:52 +05:00
Alex Ant e184ce9465 chore(release): publish [PROD]
- terminal@0.1.3
2024-07-10 15:19:02 +05:00
Alex Ant d66333b447 chore(release): publish [TESTNET]
- terminal@0.1.3-testnet.0
2024-07-10 15:18:11 +05:00
Alex Ant 73e4ca226a feat(terminal): добавлена поддержка новых команд 2024-07-10 15:17:44 +05:00
Alex Ant 7069f07579 chore(release): publish
- terminal@0.1.2
2024-07-10 14:56:19 +05:00
Alex Ant e121f34c3a chore(release): publish
- terminal@0.1.2-testnet.0
2024-07-10 14:47:41 +05:00
Alex Ant 989b3180de fix(terminal): исправлено описание проекта 2024-07-10 14:45:56 +05:00
Alex Ant 114b6b6ba2 docs(terminal): обновлен README файл 2024-07-10 14:44:38 +05:00
Alex Ant e0b510799b feat(package): добавлен скрипт gpt-commit для удобного коммита 2024-07-10 12:54:26 +05:00
Alex Ant 7237d98c82 chore(commitgpt): обновлены настройки модели 2024-07-10 12:51:25 +05:00
Alex Ant fdf999619d fix(terminal): fix typo in README.md 2024-07-10 12:47:03 +05:00
Alex Ant e6d71b4cd4 n 2024-07-10 12:43:30 +05:00
Alex Ant 9dae25c8d9 chore(release): publish
- cooparser-ts@1.0.7
 - coopback@1.7.8
 - coopdoc-generator-ts@1.0.60
 - cooptypes@1.0.11
 - coop-notificator@0.0.7
 - terminal@0.1.1
2024-07-10 12:36:19 +05:00
Alex Ant d748798c7a chore(release): publish
- cooparser-ts@1.0.7-testnet.0
 - coopback@1.7.8-testnet.0
 - coopdoc-generator-ts@1.0.60-testnet.0
 - cooptypes@1.0.11-testnet.0
 - coop-notificator@0.0.7-testnet.0
 - terminal@0.1.1-testnet.0
2024-07-10 12:32:57 +05:00
Alex Ant 21ce6bd84e n 2024-07-10 12:31:38 +05:00
Alex Ant 0e1000df25 chore(release): publish
- terminal@0.1.0
2024-07-10 12:28:57 +05:00
Alex Ant fa9786c642 chore(release): publish
- terminal@0.1.0-testnet.0
2024-07-10 12:28:26 +05:00
Alex Ant cd59f6e436 n 2024-07-10 12:27:36 +05:00
Alex Ant 31b98ffa73 n 2024-07-10 12:27:11 +05:00
Alex Ant 0a1fdfbfd5 n 2024-07-10 12:26:40 +05:00
Alex Ant a57b50f9df chore(release): publish
- terminal@0.0.19
2024-07-10 12:25:55 +05:00
Alex Ant db1e219f9e chore(release): publish
- terminal@0.0.19-testnet.0
2024-07-10 12:25:17 +05:00
Alex Ant 15feac55f2 n 2024-07-10 12:23:59 +05:00
Alex Ant 8e41d974dc n 2024-07-10 12:23:34 +05:00
Alex Ant ea723d95a0 chore(release): publish
- terminal@0.0.18
2024-07-10 12:23:06 +05:00
Alex Ant c509007d91 chore(release): publish
- terminal@0.0.18-testnet.0
2024-07-10 12:22:29 +05:00
Alex Ant d850ade896 n 2024-07-10 12:21:20 +05:00
Alex Ant 3adb4caf18 chore(release): publish
- terminal@0.0.17
2024-07-10 12:20:22 +05:00
Alex Ant b00dd79aa7 chore: dummmy commit for release 2024-07-10 12:14:36 +05:00
Alex Ant b046744d60 chore(release): publish
- terminal@0.0.17-testnet.0
2024-07-10 12:12:15 +05:00
Alex Ant 5426662ed1 n 2024-07-10 12:11:48 +05:00
Alex Ant 89e7855642 chore(release): publish
- terminal@0.0.17-beta.0
2024-07-10 12:08:24 +05:00
Alex Ant 248c2a1687 n 2024-07-10 12:08:02 +05:00
Alex Ant 0dc0ac94e2 n 2024-07-10 12:05:14 +05:00
Alex Ant 312ff470cf chore(release): publish
- terminal@0.0.14-testnet.0
2024-07-10 11:53:40 +05:00
Alex Ant 36c5b4a96d n 2024-07-10 11:53:03 +05:00
Alex Ant 7892b0486c chore(release): publish
- terminal@0.0.13
2024-07-10 11:52:00 +05:00
Alex Ant 79f43f7622 n 2024-07-10 11:50:29 +05:00
Alex Ant d038dadbc5 chore(release): publish
- terminal@0.0.13-testnet.0
2024-07-10 11:47:34 +05:00
Alex Ant d05fca5c8a n 2024-07-10 11:46:02 +05:00
Alex Ant 9d2c43372b n 2024-07-10 11:45:45 +05:00
Alex Ant 4395653bb2 chore(release): publish
- terminal@0.0.13-alpha.0
2024-07-10 11:45:09 +05:00
Alex Ant 82ada7e23d n 2024-07-10 11:43:32 +05:00
Alex Ant ebbf5254d2 chore(release): publish
- terminal@0.0.12
2024-07-10 11:43:06 +05:00
Alex Ant f274cd1180 n 2024-07-10 11:41:27 +05:00
Alex Ant ef6fb25704 chore(release): publish
- terminal@0.0.12-testnet.1
2024-07-10 11:39:36 +05:00
Alex Ant 05b4fd1497 n 2024-07-10 11:39:01 +05:00
Alex Ant cae0ffe587 chore(release): publish
- terminal@0.0.12-testnet.0
2024-07-10 11:38:35 +05:00
Alex Ant 9519a99f10 n 2024-07-10 11:37:43 +05:00
Alex Ant 65fe03be9e chore(release): publish
- terminal@0.0.11-testnet.5
2024-07-10 11:37:26 +05:00
Alex Ant 659a530b82 u 2024-07-10 11:36:47 +05:00
Alex Ant cb4c5ab21b chore(release): publish
- terminal@0.0.11-testnet.4
2024-07-10 11:34:42 +05:00
Alex Ant 80c94853fa update 2024-07-10 11:33:52 +05:00
Alex Ant eb44c23a6d chore(release): publish
- terminal@0.0.11-testnet.3
2024-07-10 11:33:21 +05:00
Alex Ant 0e59e19dba n 2024-07-10 11:32:35 +05:00
Alex Ant b39fdbb5f3 update 2024-07-10 11:30:44 +05:00
Alex Ant dfee39be0a update 2024-07-10 11:29:18 +05:00
Alex Ant 54040f5fe1 chore(release): publish
- terminal@0.0.11-testnet.2
2024-07-10 11:28:43 +05:00
Alex Ant 2737bfd2e8 update 2024-07-10 11:28:25 +05:00
Alex Ant 2dbf3feac5 updat 2024-07-10 11:28:06 +05:00
Alex Ant ad7b63cee1 chore(release): publish
- terminal@0.0.11-testnet.1
2024-07-10 11:26:41 +05:00
Alex Ant d03507412c not 2024-07-10 11:26:22 +05:00
Alex Ant 532a1f3655 nothing 2024-07-10 11:25:46 +05:00
Alex Ant a54023cba9 chore(release): publish
- terminal@0.0.11-testnet.0
2024-07-10 11:23:59 +05:00
Alex Ant b59fc1ba1a n 2024-07-10 11:23:40 +05:00
Alex Ant 6800b74359 nothing 2024-07-10 11:22:40 +05:00
Alex Ant da409e0544 nothing 2024-07-10 11:20:46 +05:00
Alex Ant a4d95c399d chore(release): publish
- terminal@0.0.10
2024-07-10 11:18:50 +05:00
Alex Ant 4501f0a196 update 2024-07-10 11:18:32 +05:00
Alex Ant 1c33733a98 update 2024-07-10 11:17:12 +05:00
Alex Ant b34d9be962 update 2024-07-10 11:13:16 +05:00
Alex Ant 39704f5d1e update 2024-07-10 11:11:44 +05:00
Alex Ant 0458160061 chore(release): publish
- terminal@0.0.9
2024-07-10 11:09:29 +05:00
Alex Ant fc7971bb97 update 2024-07-10 11:08:02 +05:00
Alex Ant d56b1b565a update 2024-07-10 11:05:56 +05:00
Alex Ant 224e927d76 save 2024-07-10 11:03:08 +05:00
Alex Ant 84c9bdc5b3 chore(release): publish
- coopback@1.7.7
 - terminal@0.0.8
2024-07-10 10:55:13 +05:00
Alex Ant 3f7caa046b update 2024-07-10 10:48:28 +05:00
Alex Ant 810e9e2e3a update 2024-07-10 10:46:19 +05:00
Alex Ant 6422f9b5ca chore(release): publish
- cooparser-ts@1.0.6
 - coopback@1.7.6
 - coopdoc-generator-ts@1.0.59
 - cooptypes@1.0.10
 - coop-notificator@0.0.6
 - terminal@0.0.7
2024-07-10 10:14:05 +05:00
Alex Ant cd5e7b1daa init 2024-07-10 10:12:56 +05:00
12713 changed files with 913700 additions and 349408 deletions
+11
View File
@@ -0,0 +1,11 @@
Предложи 10 сообщений о коммите, основанных на следующем diff: {{diff}}
Сообщениях о коммитах должны:
- следовать conventional commits
- формат сообщения должен быть: <type>[scope]: <description>
примеры:
- fix(authentication): добавлен regex для пароля
- feat(storage): добавлены новые тесты
+5
View File
@@ -0,0 +1,5 @@
{
"model": "gpt-3.5-turbo-instruct",
"temperature": 0.5,
"maxTokens": 2048
}
+3
View File
@@ -0,0 +1,3 @@
{
"agentCanUpdateSnapshot": true
}
+8
View File
@@ -0,0 +1,8 @@
---
description:
globs:
alwaysApply: true
---
ВАЖНО!!! Мы работаем в МОНО-репозитории pnpm, любая установка пакетов производится ЧЕРЕЗ ФИЛЬТР компонента в корне: pnpm add glob --filter notificator2.
ВАЖНО!!! НИКОГДА НЕ ЗАПУСКАЙ ПРИЛОЖЕНИЕ ИЛИ ЕГО СБОРКУ!!! Просто отчитайся что всё сделал.
+151
View File
@@ -0,0 +1,151 @@
---
description:
globs: components/controller/**
alwaysApply: false
---
# NestJS Controller и Чистая архитектура
## Основные принципы
1. Чистая архитектура - главный архитектурный подход. Пиши код с комментариями.
2. Типы IName, IChecksum256, ITimePointSec - это просто строки.
3. Домен должен быть полностью изолирован от инфраструктурных деталей.
4. Направление зависимостей - внутрь (к ядру, домену).
5. Домен, инфраструктура и приложение связаны через App.module, НЕ НУЖНО импортировать их друг в друга, а достаточно просто импортировать домен на уровне приложения чтобы использовать все экспорты домена.
## Структура проекта
- `domain/` - доменный слой (бизнес-логика, независимая от инфраструктуры)
- `infrastructure/` - инфраструктурный слой (адаптеры к внешним системам)
- `modules/` - слой приложения (DTO, резолверы, сервисы)
## Слои и их взаимодействие
1. **Домен**:
- Содержит чистые доменные интерфейсы и реализованные на них сущности
- НЕ должен зависеть от `cooptypes` (инфраструктурный контракт)
- Использует собственные доменные типы (например, Date вместо строковых timestamp)
- Интерфейсы портов описывают взаимодействие с внешними системами
2. **Инфраструктура**:
- Содержит адаптеры к внешним системам (блокчейн, БД и т.д.)
- Осуществляет преобразование между доменными и инфраструктурными типами
- Общая логика преобразования выносится в утилитарные классы (например, `DomainToBlockchainUtils`)
3. **Модули (приложение)**:
- DTO имплементируют доменные интерфейсы напрямую
- Резолвер вызывает сервис, который принимает DTO
- Сервис передает объекты DTO в интерактор домена
## Поток данных
1. Резолвер принимает входные данные и передает их в сервис
2. Сервис вызывает интерактор домена, передавая ему объекты DTO (имплементирующие доменный интерфейс)
3. Интерактор выполняет бизнес-логику и взаимодействует с портами домена
4. Адаптеры (инфраструктурный слой) преобразуют доменные объекты в формат внешних систем (JSON для хранения мета-данных, ISO для дат и т.д.)
5. Адаптеры возвращают результаты в домен, домен возвращает данные в сервис, который возвращает их в резолвер
## Правила преобразования данных
1. Преобразование DTO → доменный объект: не требуется, если DTO имплементирует доменный интерфейс
2. Преобразование доменный объект → инфраструктурный тип: происходит в адаптерах
3. Преобразование документов, дат и других сложных объектов: используются утилитарные классы уровня инфраструктуры
## Работа с типами данных
1. **Даты**:
- В доменных интерфейсах используется тип `Date`
- В DTO используется тип `Date` с декораторами `@IsDate()` и `@Type(() => Date)`
- В инфраструктурном слое происходит преобразование `Date` → `string` (ISO формат)
```typescript
// Доменный интерфейс
interface MeetDomainInterface {
open_at: Date;
}
// DTO
@Field(() => Date)
@IsDate()
@Type(() => Date)
open_at!: Date;
// Адаптер
const blockchainData = {
open_at: domainToBlockchainUtils.convertDateToBlockchainFormat(data.open_at)
};
```
2. **Документы**:
- В доменных интерфейсах используется собственный тип `SignedDocumentDomainInterface<T>`
- В DTO используется соответствующий DTO-класс (например, `SignedDigitalDocumentInputDTO`)
- В инфраструктурном слое происходит преобразование между форматами (meta-поля в JSON и т.д.)
## Типовые ошибки
1. **Нарушение изоляции домена**: домен должен быть изолирован от инфраструктуры. Не используйте импорты из `cooptypes` в доменных интерфейсах.
```typescript
// Неправильно
import { MeetContract } from 'cooptypes';
export type VoteDomainInterface = MeetContract.Actions.Vote.IInput;
// Правильно
export interface VoteDomainInterface {
coopname: string;
hash: string;
// ... доменные поля
}
```
2. **Преобразование в неправильном слое**: преобразование доменных объектов в инфраструктурные типы должно происходить в адаптерах, а не в доменном слое или сервисе.
```typescript
// Неправильно (в доменном интеракторе)
async vote(data: VoteDomainInterface) {
const blockchainData = { ...data, meta: JSON.stringify(data.meta) };
// ...
}
// Правильно (в адаптере)
async vote(data: VoteDomainInterface) {
const blockchainData = this.convertToBlockchainFormat(data);
// ...
}
```
3. **Дублирование логики преобразования**: общая логика преобразования должна быть вынесена в утилитарные классы.
```typescript
// Неправильно (дублирование в разных адаптерах)
// В MeetAdapter
private convertDoc(doc) { return { ...doc, meta: JSON.stringify(doc.meta) }; }
// В BranchAdapter
private convertDoc(doc) { return { ...doc, meta: JSON.stringify(doc.meta) }; }
// Правильно (общий утилитарный класс)
// DomainToBlockchainUtils
convertSignedDocumentToBlockchainFormat(doc) {
return { ...doc, meta: JSON.stringify(doc.meta) };
}
```
## Примеры
```typescript
// Доменный интерфейс - чистый, без зависимостей от инфраструктуры
export interface VoteOnAnnualGeneralMeetInputDomainInterface {
coopname: string;
hash: string;
member: string;
ballot: VoteItemInputDomainInterface[];
}
// DTO имплементирует доменный интерфейс напрямую
@InputType('VoteOnAnnualGeneralMeetInput')
export class VoteOnAnnualGeneralMeetInputDTO implements VoteOnAnnualGeneralMeetInputDomainInterface {
@Field(() => String)
@IsString()
coopname!: string;
// ... остальные поля
}
// Адаптер преобразует доменный объект в инфраструктурный тип
async vote(data: VoteOnAnnualGeneralMeetInputDomainInterface): Promise<TransactionResult> {
// Преобразуем доменный объект в инфраструктурный тип
const blockchainData: MeetContract.Actions.Vote.IInput = {
coopname: data.coopname,
hash: data.hash,
// ... преобразование других полей
};
// ... отправка данных во внешнюю систему
}
```
@@ -0,0 +1,41 @@
---
description: SDK мутации и запросы для подключения на рабочем столе
globs:
alwaysApply: false
---
Бэкенд реализован здесь components/controller, sdk здесь components/sdk.
Пример создания Query к API через SDK:
``` ts
async function loadBranches(data: IGetBranchesInput): Promise<IBranch[]> {
const { [Queries.Branches.GetBranches.name]: output } = await client.Query(
Queries.Branches.GetBranches.query,
{
variables: {
data
}
}
);
return output;
}
```
Такие запросы обычно хранятся в папке Entities и вызываются из его store.
Пример мутации:
``` ts
async function selectBranch(data: ISelectBranchInput): Promise<boolean>{
const {[Mutations.Branches.SelectBranch.name]: result} = await client.Mutation(Mutations.Branches.SelectBranch.mutation, {variables: {
data
}})
return result
}
```
Мутации обычно храним в папке features.
Как можешь обратить внимание, все мутации и запросы строятся по одному шаблону. Вся необходимая информация уже есть в SDK.
+12
View File
@@ -0,0 +1,12 @@
---
alwaysApply: true
globs: **/desktop/**
---
# DESKTOP
- Пишем код фронтенда в архитектуре Feature Sliced Design (FSD).
- Стиль шаблонов PUG на composite API.
- Всегда создаём index.ts файлы для vue компонент.
- Создавай индексные файлы для vue через export {default as NAME} from './where', а на уровне выше, если это необходимо, делай export * from './ui'
- Всегда удаляем неиспользуемые импорты.
- Не используем emit избыточно. Вместо них используем композабл функции моделей фич, если необходимо. Emit только в крайнем случае.
+62
View File
@@ -0,0 +1,62 @@
---
description:
globs:
alwaysApply: false
---
Файл [main.py](mdc:monocoop/monocoop/monocoop/components/docs/main.py) автоматически генерит ссылки на документацию SDK и GraphQL, которые формируются и публикуются автоматически. При создании документации к методам всегда применяй ссылки на SDK и GraphQL по форме:
{{ get_sdk_doc("Mutations", "Accounts", "RegisterAccount") }} | {{ get_graphql_doc("Mutation.registerAccount") }}
### 🎯 Основные паттерны использования
**1. Стандартная структура для методов API:**
```markdown
## Название действия
{{ get_sdk_doc("Namespace", "Module", "Method") }} | {{ get_graphql_doc("Type.methodName") }}
{{ get_typedoc_input("Namespace.Module.Method") }}
Результат:
{{ get_typedoc_definition("Namespace.Module.Method", "IOutput") }}
```
**2. Описание + пример (для сложных методов):**
```markdown
{{ get_typedoc_desc("Namespace.Module.Method") }}
{{ get_typedoc_input("Namespace.Module.Method") }}
```
**3. Ссылки на типы данных:**
```markdown
У каждого аккаунта есть объект {{ get_graphql_definition("Account") }} в GraphQL-API
```
### 🔧 Макросы и их применение
| Макрос | Назначение | Пример использования |
|--------|------------|---------------------|
| `get_sdk_doc` | Ссылка на SDK документацию | `{{ get_sdk_doc("Mutations", "Payments", "CreateDeposit") }}` |
| `get_graphql_doc` | Ссылка на GraphQL операцию | `{{ get_graphql_doc("Query.getAccount") }}` |
| `get_graphql_definition` | Ссылка на GraphQL тип | `{{ get_graphql_definition("Account") }}` |
| `get_class_doc` | Ссылка на класс/метод SDK | `{{ get_class_doc("Document", "sign") }}` |
| `get_typedoc_input` | **Полный пример** TypeScript вызова | `{{ get_typedoc_input("Mutations.Auth.Login") }}` |
| `get_typedoc_definition` | **Структура интерфейса** | `{{ get_typedoc_definition("Mutations.Auth.Login", "IOutput") }}` |
| `get_typedoc_desc` | Описание + примеры | `{{ get_typedoc_desc("Mutations.Auth.Login") }}` |
| `get_typedoc_value` | Значение константы | `{{ get_typedoc_value("Constants.API_VERSION") }}` |
### 📝 Правила оформления
**ОБЯЗАТЕЛЬНО:**
- Всегда используй `get_typedoc_input` для демонстрации **КАК вызывать** метод
- Всегда используй `get_typedoc_definition` для показа **ЧТО возвращается**
- Комбинируй SDK и GraphQL ссылки через ` | `: `{{ get_sdk_doc(...) }} | {{ get_graphql_doc(...) }}`
**ЖЕЛАТЕЛЬНО:**
- Для сложных методов добавляй `get_typedoc_desc` в начало
- Используй `get_graphql_definition` для ссылок на типы данных в тексте
- Группируй связанные операции в одном разделе
**ФОРМАТ ССЫЛОК:**
- SDK: `"Namespace", "Module", "Method"` (3 аргумента)
- GraphQL: `"Type.methodName"` (точка между типом и методом)
- Определения: просто имя типа `"TypeName"`
+96
View File
@@ -0,0 +1,96 @@
---
description:
globs:
alwaysApply: false
---
# Структура файлов шаблонов документов и алгоритм правки
## Основные директории и файлы
### 1. Определение типов и интерфейсов (cooptypes)
**Путь:** `/cooptypes/src/cooperative/registry/[ID.DocumentName]/index.ts`
В этих файлах определяются:
- Интерфейсы данных (`IAgendaMeet`, etc.)
- Основная модель данных документа (`Model`)
- HTML шаблон документа (`context`)
- Переводы строк (`translations`)
- Пример данных для тестирования (`exampleData`)
**Для изменения шаблона нужно править:**
- Интерфейсы модели данных при изменении структуры
- HTML в переменной `context` для изменения внешнего вида
- Строки переводов в `translations.ru`
### 2. Схемы валидации (factory)
**Путь:** `/factory/src/Schema/[SchemaName].ts`
Содержат:
- JSON схемы для валидации данных
- Определение обязательных полей
**При изменении структуры данных:**
- Обновите соответствующую схему валидации
- Обновите список обязательных полей в `required`
### 3. Фабрики документов (factory)
**Путь:** `/factory/src/Actions/[ID.DocumentName].ts`
Обрабатывают:
- Получение данных из разных источников
- Сборку модели для шаблонизатора
- Валидацию данных по схеме
- Генерацию PDF
**При изменении логики сборки документа:**
- Обновите метод `generateDocument()`
- Добавьте новые источники данных
### 4. Шаблоны (factory)
**Путь:** `/factory/src/Templates/[ID.DocumentName].ts`
Связывают:
- Шаблон из cooptypes
- Схему валидации
- Метаданные документа
**После изменения в cooptypes:**
- Убедитесь, что схема в Templates соответствует новой модели
### 5. Тесты (factory)
**Путь:** `/factory/test/[category].test.ts`
Содержат:
- Тестовые данные для генерации документов
- Вызовы функции `testDocumentGeneration`
**После внесения изменений:**
- Обновите тестовые данные в соответствии с новой структурой
- Запустите тесты командой `pnpm test`
## Алгоритм внесения изменений
1. **Модификация типов**
- Изменить файл в `/cooptypes/src/cooperative/registry/[ID.DocumentName]/index.ts`
- Обновить интерфейсы, шаблон HTML и переводы
2. **Обновление схемы валидации**
- Изменить соответствующую схему в `/factory/src/Schema/`
- Убедиться, что обязательные поля совпадают с интерфейсом
3. **Компиляция библиотеки типов**
- Выполнить `cd /cooptypes && pnpm build`
4. **Обновление тестовых данных**
- Привести тестовые данные в соответствие с новой структурой
5. **Запуск тестов**
- Выполнить `cd /factory && pnpm test [filename].test.ts`
## Особенности шаблонизации
- Используется Nunjucks для шаблонов
- Поддерживаются конструкции: `{% if %}`, `{% for %}`, `{% trans %}`
- Переменные вставляются через `{{ variable }}`
- Переводы через `{% trans 'KEY' %}`
+225
View File
@@ -0,0 +1,225 @@
# Архитектура расширений в MonoCoop
## Основные принципы
1. Расширения построены на модулях NestJS с использованием шаблона "Порты и адаптеры"
2. Каждое расширение наследуется от `BaseExtModule` и реализует интерфейс `OnModuleInit`
3. Расширения могут взаимодействовать с блокчейном через соответствующие порты
4. Конфигурации расширений хранятся в БД и описываются с помощью Zod-схем
5. Расширения регистрируются в глобальном реестре `AppRegistry`
## Структура расширения
Минимальная структура расширения включает:
- `XXX-extension.module.ts` - основной модуль расширения
- `package.json` - информация о пакете
- `README.md` - документация
- `INSTALL.md` - инструкции по установке
- `CHANGELOG.md` - история изменений
## Создание нового расширения
1. Создайте директорию для расширения в `components/controller/src/extensions/`
2. Создайте основной класс расширения, наследующийся от `BaseExtModule`
3. Определите Zod-схему для конфигурации
4. Реализуйте метод `initialize()`
5. Зарегистрируйте расширение в `extensions.registry.ts`
6. Добавьте расширение в список дефолтных приложений в `extension-domain.service.ts`
## Пример структуры модуля расширения
```typescript
// XXX-extension.module.ts
export class XXXPlugin extends BaseExtModule {
constructor(...) {
super();
}
name = 'xxx';
plugin!: ExtensionDomainEntity<IConfig>;
public configSchemas = Schema;
async initialize() {
// Инициализация расширения
// Настройка cron-задач
}
}
@Module({
providers: [XXXPlugin],
})
export class XXXPluginModule {
constructor(private readonly xxxPlugin: XXXPlugin) {}
async initialize() {
await this.xxxPlugin.initialize();
}
}
```
## Управление отображением конфигурации
Zod-схемы используются для автоматического отображения формы настроек в интерфейсе пользователя.
Через интерфейс `DeserializedDescriptionOfExtension` из `components/controller/src/types/shared/extension.types.ts`
можно управлять отображением полей формы:
```typescript
export const Schema = z.object({
// Базовое поле с меткой
simpleField: z.string().describe(
describeField({
label: 'Название поля',
note: 'Подсказка под полем'
})
),
// Скрытое поле для служебного использования
hiddenField: z.string().describe(
describeField({
label: 'Скрытое поле',
visible: false
})
),
// Поле с проверкой значения
validatedField: z.number().describe(
describeField({
label: 'Поле с валидацией',
rules: ['val >= 5', 'val <= 100'],
})
),
// Форматированное поле с префиксом и суффиксом
formattedField: z.number().describe(
describeField({
label: 'Форматированное поле',
prepend: '$',
append: 'USD',
})
),
// Многострочное текстовое поле
multilineField: z.string().describe(
describeField({
label: 'Многострочное поле',
maxRows: 5,
minLength: 10,
maxLength: 1000
})
),
});
```
Доступные поля для управления отображением:
- `label` - название поля (обязательное)
- `note` - пояснение или подсказка
- `visible` - видимость поля (по умолчанию true)
- `rules` - правила валидации в виде строковых выражений
- `mask` - маска для ввода
- `fillMask` - автозаполнение маски
- `minLength` / `maxLength` - ограничения длины для текстовых полей
- `maxRows` - количество строк для многострочного ввода
- `append` / `prepend` - текст до/после значения поля
## Взаимодействие с блокчейном
Для взаимодействия с блокчейном:
1. Определите порт в доменном слое (например, `SovietBlockchainPort`)
2. Инжектируйте порт в конструкторе расширения через DI
3. Используйте методы порта для взаимодействия с блокчейном
```typescript
@Inject(SOVIET_BLOCKCHAIN_PORT) private readonly sovietBlockchainPort: SovietBlockchainPort
// ...
const decisions = await this.sovietBlockchainPort.getDecisions(coopname);
```
## Настройка планировщика задач
Расширения могут использовать cron-задачи для периодического выполнения операций:
```typescript
import cron from 'node-cron';
// Регистрация cron-задачи (каждые N минут)
const cronExpression = `*/${this.plugin.config.checkInterval} * * * *`;
cron.schedule(cronExpression, () => {
this.logger.info('Запуск запланированной задачи');
this.runTask();
});
```
## Работа с конфигурацией
1. Определите Zod-схему для конфигурации
2. Используйте `describeField` для добавления UI-метаданных к полям
3. Получайте и обновляйте конфигурацию через репозиторий `extensionRepository`
```typescript
export const Schema = z.object({
checkInterval: z.number().describe(
describeField({
label: 'Интервал проверки (в минутах)',
note: 'Минимум: 5 минут',
rules: ['val >= 5'],
})
),
});
// Обновление конфигурации
this.plugin.config.lastCheckDate = new Date().toISOString();
await this.extensionRepository.update(this.plugin);
```
## Логирование действий
Расширения должны логировать свои действия:
1. Используйте `WinstonLoggerService` для системного логирования
2. Используйте `LogExtensionDomainRepository` для хранения логов в БД
```typescript
// Системное логирование
this.logger.info(`Выполнение операции для ${id}`);
// Сохранение лога в БД
await this.logExtensionRepository.push(this.name, {
type: 'operation',
timestamp: new Date().toISOString(),
data: { ... },
});
```
## Регистрация расширения
После создания расширения, добавьте его в `extensions.registry.ts`:
```typescript
export const AppRegistry: INamedExtension = {
myExtension: {
is_builtin: false,
is_internal: true,
is_available: true,
is_desktop: false,
title: 'Моё расширение',
description: 'Описание функциональности.',
image: 'https://example.com/image.png',
class: MyExtensionPluginModule,
schema: MyExtensionSchema,
tags: ['тег1', 'тег2'],
readme: getReadmeContent('./myExtension'),
instructions: getInstructionsContent('./myExtension'),
},
};
```
## Дефолтные настройки
Добавьте расширение в список дефолтных приложений в `extension-domain.service.ts`:
```typescript
getDefaultApps(): Partial<ExtensionDomainEntity>[] {
return [
// ...
{
name: 'myExtension',
enabled: true,
config: {
// Дефолтные значения конфигурации
parameter1: 'value1',
parameter2: 42,
},
},
// ...
];
}
```
+168
View File
@@ -0,0 +1,168 @@
---
description:
globs: **/controller/src/extensions/**
alwaysApply: false
---
# Архитектура расширений в MonoCoop
## Основные принципы
1. Расширения построены на модулях NestJS с использованием шаблона "Порты и адаптеры"
2. Каждое расширение наследуется от `BaseExtModule` и реализует интерфейс `OnModuleInit`
3. Расширения могут взаимодействовать с блокчейном через соответствующие порты
4. Конфигурации расширений хранятся в БД и описываются с помощью Zod-схем
5. Расширения регистрируются в глобальном реестре `AppRegistry`
## Структура расширения
Минимальная структура расширения включает:
- `XXX-extension.module.ts` - основной модуль расширения
- `package.json` - информация о пакете
- `README.md` - документация
- `INSTALL.md` - инструкции по установке
- `CHANGELOG.md` - история изменений
## Создание нового расширения
1. Создайте директорию для расширения в `components/controller/src/extensions/`
2. Создайте основной класс расширения, наследующийся от `BaseExtModule`
3. Определите Zod-схему для конфигурации
4. Реализуйте метод `initialize()`
5. Зарегистрируйте расширение в `extensions.registry.ts`
6. Добавьте расширение в список дефолтных приложений в `extension-domain.service.ts`
## Пример структуры модуля расширения
```typescript
// XXX-extension.module.ts
export class XXXPlugin extends BaseExtModule {
constructor(...) {
super();
}
name = 'xxx';
plugin!: ExtensionDomainEntity<IConfig>;
public configSchemas = Schema;
async initialize() {
// Инициализация расширения
// Настройка cron-задач
}
// Дополнительные методы расширения
}
@Module({
providers: [XXXPlugin],
})
export class XXXPluginModule {
constructor(private readonly xxxPlugin: XXXPlugin) {}
async initialize() {
await this.xxxPlugin.initialize();
}
}
```
## Взаимодействие с блокчейном
Для взаимодействия с блокчейном:
1. Определите порт в доменном слое (например, `SovietBlockchainPort`)
2. Инжектируйте порт в конструкторе расширения через DI
3. Используйте методы порта для взаимодействия с блокчейном
```typescript
@Inject(SOVIET_BLOCKCHAIN_PORT) private readonly sovietBlockchainPort: SovietBlockchainPort
// ...
const decisions = await this.sovietBlockchainPort.getDecisions(coopname);
```
## Настройка планировщика задач
Расширения могут использовать cron-задачи для периодического выполнения операций:
```typescript
import cron from 'node-cron';
// Регистрация cron-задачи (каждые N минут)
const cronExpression = `*/${this.plugin.config.checkInterval} * * * *`;
cron.schedule(cronExpression, () => {
this.logger.info('Запуск запланированной задачи');
this.runTask();
});
```
## Работа с конфигурацией
1. Определите Zod-схему для конфигурации
2. Используйте `describeField` для добавления UI-метаданных к полям
3. Получайте и обновляйте конфигурацию через репозиторий `extensionRepository`
```typescript
export const Schema = z.object({
checkInterval: z.number().describe(
describeField({
label: 'Интервал проверки (в минутах)',
note: 'Минимум: 5 минут',
rules: ['val >= 5'],
})
),
});
// Обновление конфигурации
this.plugin.config.lastCheckDate = new Date().toISOString();
await this.extensionRepository.update(this.plugin);
```
## Логирование действий
Расширения должны логировать свои действия:
1. Используйте `WinstonLoggerService` для системного логирования
2. Используйте `LogExtensionDomainRepository` для хранения логов в БД
```typescript
// Системное логирование
this.logger.info(`Выполнение операции для ${id}`);
// Сохранение лога в БД
await this.logExtensionRepository.push(this.name, {
type: 'operation',
timestamp: new Date().toISOString(),
data: { ... },
});
```
## Регистрация расширения
После создания расширения, добавьте его в `extensions.registry.ts`:
```typescript
export const AppRegistry: INamedExtension = {
myExtension: {
is_builtin: false,
is_internal: true,
is_available: true,
is_desktop: false,
title: 'Моё расширение',
description: 'Описание функциональности.',
image: 'https://example.com/image.png',
class: MyExtensionPluginModule,
schema: MyExtensionSchema,
tags: ['тег1', 'тег2'],
readme: getReadmeContent('./myExtension'),
instructions: getInstructionsContent('./myExtension'),
},
};
```
## Дефолтные настройки
Добавьте расширение в список дефолтных приложений в `extension-domain.service.ts`:
```typescript
getDefaultApps(): Partial<ExtensionDomainEntity>[] {
return [
// ...
{
name: 'myExtension',
enabled: true,
config: {
// Дефолтные значения конфигурации
parameter1: 'value1',
parameter2: 42,
},
},
// ...
];
}
```
+261
View File
@@ -0,0 +1,261 @@
---
description:
globs: src/**/*.ts
alwaysApply: false
---
# Фабрика Документов Кооперативов
## Общая Архитектура
Фабрика документов — это система генерации PDF документов для кооперативов, построенная на TypeScript с использованием MongoDB для хранения данных. Система состоит из трех основных частей:
1. **registry/** — JSON-шаблоны документов (статические данные)
2. **factory/** — основная фабрика с логикой генерации
3. **cooptypes/** — типы данных и интерфейсы
## Структура Registry
В корневой папке `registry/` находятся JSON файлы с номерными названиями, представляющие шаблоны документов:
### Основные документы:
- `1.walletProgramAgreement.json` — соглашение о кошельке
- `2.regulationElectronicSignature.json` — регламент электронной подписи
- `3.privacyPolicy.json` — политика конфиденциальности
- `4.userAgreement.json` — пользовательское соглашение
- `50.CoopenomicsAgreement.json` — соглашение с партнерами
- `100.participantApplication.json` — заявление участника
- `101.selectBranchStatement.json` — заявление о выборе филиала
### Документы общих собраний (300-304):
- `300.annualGeneralMeetingAgenda.json` — предложение повестки дня
- `301.annualGeneralMeetingSovietDecision.json` — протокол заседания совета
- `302.annualGeneralMeetingNotification.json` — уведомление о собрании
- `303.annualGeneralMeetingVotingBallot.json` — бюллетень для голосования
- `304.annualGeneralMeetingDecision.json` — протокол общего собрания
### Инвестиционные документы (1000+):
- `1000.investAgreement.json` — инвестиционное соглашение
- `1001.investByResultStatement.json` — заявление о зачете по результатам
- `1002.investByResultAct.json` — акт зачета по результатам
- `1005.investByMoneyStatement.json` — заявление о зачете денежных средств
### Структура JSON-шаблона:
```json
{
"context": "<div>...HTML шаблон с переменными...</div>",
"model": {...данные для примера...},
"translation": {...переводы ключей...},
"object_model": {...схема объектной модели...}
}
```
## Фабрика (factory/)
### Основные компоненты:
#### src/index.ts — Главный класс Generator
```typescript
export class Generator implements IGenerator {
// Хранилище фабрик для каждого типа документа
factories: { [K in Numbers]: DocFactory<IGenerate> }
// MongoDB коннектор
public storage: MongoDBConnector
// Основной метод генерации
async generate(data: IGenerate, options?: IGenerationOptions): Promise<IGeneratedDocument>
}
```
#### Архитектура Factory Pattern:
- Базовый класс `DocFactory<T>` в `src/Factory/index.ts`
- Каждый документ имеет свою фабрику в `src/Actions/`
- Фабрики наследуются от `DocFactory` и реализуют метод `generateDocument()`
### Сервисы:
#### Services/Generator/ — PDF генерация
- `PDFService` — конвертирует HTML в PDF через WeasyPrint
- Использует шрифт Arial (base64)
- Добавляет метаданные в PDF
- Вычисляет SHA-256 хеш документа
#### Services/Templator/ — Шаблонизация
- Основан на Nunjucks
- Поддерживает кастомное расширение `{% trans %}` для переводов
- Рендерит HTML из шаблона с подстановкой переменных
#### Services/Validator/ — Валидация
- Использует AJV для JSON Schema валидации
- Поддерживает кастомные форматы (телефон)
- Локализация ошибок на русском языке
#### Services/Databazor/ — База данных
- `MongoDBConnector` — работа с MongoDB
- `DataService` — абстракция над данными
- Коллекции: `deltas`, `actions`, `documents`, и другие
### Модели данных (src/Models/):
#### Основные типы пользователей:
- `Individual` — физические лица (ФИО, паспорт, адрес)
- `Organization` — организации (ИНН, ОГРН, представитель)
- `Entrepreneur` — ИП (ФИО + ИНН/ОГРН)
#### Кооперативные данные:
- `Cooperative` — данные кооператива
- `PaymentMethod` — платежные методы
- `Vars` — переменные кооператива
- `Project` — проекты
### Система Action-ов:
Каждый документ имеет Action класс в `src/Actions/` с методом `generateDocument()`:
1. **Получение шаблона** — из локального Registry или MongoDB
2. **Сбор данных** — пользователь, кооператив, переменные, специфичные данные
3. **Валидация** — проверка по JSON схеме
4. **Рендеринг** — HTML из шаблона + данные
5. **PDF генерация** — HTML → PDF с метаданными
6. **Сохранение** — в MongoDB (если не skip_save)
## Система типов (cooptypes/)
### cooperative/registry/ — Типы документов
Каждый документ имеет папку с интерфейсами:
- `Action` — входные данные для генерации
- `Model` — модель данных для шаблона
- `Template` — структура шаблона
### contracts/ — Блокчейн контракты
- `registrator/` — регистрация кооперативов
- `soviet/` — управление советом
- `meet/` — общие собрания
- `wallet/`, `capital/`, `fund/` — финансовые операции
## База данных MongoDB
### Основные коллекции:
#### deltas — Состояние блокчейна
```javascript
{
block_num: number,
present: boolean,
code: string, // название контракта
scope: string, // область действия
table: string, // имя таблицы
primary_key: string,
value: {...} // данные записи
}
```
#### actions — Действия блокчейна
```javascript
{
block_num: number,
account: string,
name: string, // имя действия
receiver: string,
data: {...} // данные действия
}
```
#### documents — Сгенерированные документы
```javascript
{
hash: string, // SHA-256 хеш
binary: Uint8Array, // PDF данные
html: string, // HTML исходник
meta: { // метаданные
title: string,
created_at: string,
lang: string
}
}
```
### Таблицы данных:
- `coops` — кооперативы
- `meets` — собрания
- `questions` — вопросы собраний
- `decisions` — решения совета
- `individuals` — физические лица
- `organizations` — организации
- `entrepreneurs` — ИП
- `paymentMethods` — платежные методы
- `vars` — переменные кооперативов
## Генерация документов
### Процесс генерации:
1. **Вызов** `generator.generate(action, options)`
2. **Поиск фабрики** по `registry_id`
3. **Загрузка шаблона** (локально или из БД)
4. **Сбор данных** из MongoDB по `coopname`, `username`, `block_num`
5. **Создание модели** — объединение всех данных
6. **Валидация** модели по JSON схеме
7. **Рендеринг HTML** через Nunjucks
8. **Генерация PDF** через WeasyPrint
9. **Добавление метаданных** в PDF
10. **Вычисление хеша** SHA-256
11. **Сохранение** в MongoDB
### Пример использования:
```typescript
const generator = new Generator()
await generator.connect(mongoUri)
const document = await generator.generate({
registry_id: '300',
coopname: 'voskhod',
username: 'ant',
block_num: 0,
meet: {...},
questions: [...]
})
```
## Особенности реализации
### Шаблонизация:
- HTML шаблоны с CSS стилями
- Переменные в формате `{{variable.field}}`
- Условная логика `{% if condition %}`
- Циклы `{% for item in array %}`
- Переводы `{% trans 'KEY', var1, var2 %}`
### Подписи:
- Цифровые подписи вместо физических
- Текст "Подписано электронной подписью"
- Убраны подчеркивания для подписей
### Типы собраний:
- `regular` — очередное
- `extraordinary` — внеочередное
- Условная логика в шаблонах
### Филиалы:
- `coop.is_branched` — проверка на наличие филиалов
- "пайщиков" vs "уполномоченных" в зависимости от типа
### Форматирование дат:
- Формат: "г. Москва, 15 декабря 2024 г."
- Без кавычек вокруг дат
- Запятая после города
## Тестирование
### test/utils/index.ts — Тестовые утилиты:
- `preLoading()` — инициализация тестовых данных
- Создание кооператива, пользователей, платежных методов
- Настройка данных собраний и решений
- Очистка временных файлов
### Тестовые данные:
- Кооператив "ВОСХОД"
- Пользователи: ant, individual, entrepreneur
- Организации: voskhod, branch, exampleorg
- Собрания с вопросами и решениями
Фабрика поддерживает полный цикл создания документов кооператива от заявлений до протоколов собраний с возможностью кастомизации под разные типы кооперативов и требования.
+59
View File
@@ -0,0 +1,59 @@
---
description:
globs: components/sdk/**
alwaysApply: false
---
# Руководство по работе с GraphQL Zeus в SDK
## Основной процесс
1. **Анализ DTO бэкенда**:
- Изучите структуру DTO классов (`@ObjectType`) в бэкенде
- Обратите внимание на имена типов в декораторах `@ObjectType('ИмяТипа')`
- Отметьте поля, связи и вложенные объекты
2. **Создание селекторов**:
- Для каждого DTO создайте соответствующий селектор с именем `raw<ИмяТипа>Selector`
- Селектор - это объект, где ключи соответствуют полям DTO, а значения - `true`
- Для вложенных объектов используйте вложенные селекторы: `field: nestedSelector`
- Для списков используйте один селектор без массива: `items: itemSelector`
3. **Валидация селекторов**:
- Для каждого селектора создайте проверку типа:
```typescript
const _validate: MakeAllFieldsRequired<ValueTypes['ТочноеИмяГрафКьЭлТипа']> = rawSelector
```
- Имя типа должно точно совпадать с именем в декораторе `@ObjectType`
4. **Экспорт селекторов**:
- Создайте финальный селектор с помощью функции `Selector`:
```typescript
export const typeSelector = Selector('ТочноеИмяГрафКьЭлТипа')(rawTypeSelector)
```
- Экспортируйте сырой селектор для переиспользования
- Экспортируйте тип модели: `export type modelType = ModelTypes['ТочноеИмяГрафКьЭлТипа']`
5. **Создание запросов/мутаций**:
- Используйте селекторы в запросах и мутациях:
```typescript
export const query = Selector('Query')({
queryName: [{ data: $('data', 'ТочноеИмяВходногоТипа!') }, exportedSelector]
})
```
- Для параметров используйте оператор `$` с точным именем входного типа
- Создайте интерфейс входных данных:
```typescript
export interface IInput {
data: ModelTypes['ТочноеИмяВходногоТипа']
}
```
## Особенности работы
- **Документы**: всегда сохраняйте структуру `{ hash, signatures, rawDocument }`
- **Сложные DTO**: разбивайте на атомарные селекторы и комбинируйте их
- **Типы в Zeus**: часто отличаются от имен классов в бэкенде, всегда проверяйте в `schema.gql`
- **Массивы**: Zeus автоматически обрабатывает массивы, не используйте `[selector]`
Это руководство поможет правильно структурировать работу с SDK и избежать типичных ошибок при работе с Zeus.
+20
View File
@@ -0,0 +1,20 @@
---
globs: notifications/src/workflows/**/*.ts
---
# Правила валидации воркфлоу
## 🚫 ID воркфлоу
- **Длина ID не должна превышать 32 символа**
- Используйте описательные, но короткие идентификаторы малыми латинскими буквами и тире.
## 🚫 Условия в шаблонах
- **Запрещено использовать JavaScript выражения в шаблонах Novu**
- Нельзя использовать:
- Тернарные операторы: `{{condition ? "text1" : "text2"}}`
- Логические операторы: `{{field && "text"}}`
- Любые другие JS конструкции
## ✅ Рекомендации
- Добавляйте текстовые поля в payload для условной логики
- Вычисляйте значения на стороне сервера перед отправкой уведомления
- Используйте только простые переменные: `{{payload.fieldName}}`
+41
View File
@@ -0,0 +1,41 @@
# Не тащить в build-context — экономит время `docker build` (особенно
# на крупных репах с .git под 1GB) и не пачкает финальный образ.
node_modules
**/node_modules
dist
**/dist
.git
.github
.gitignore
.cursor
**/.DS_Store
# State от локальных runtime-сценариев (boot:remote / dev-нода / wallet)
**/blockchain-data
**/wallet-data
**/keosd-data
# CI/coverage/тестовые артефакты
coverage
**/coverage
.nyc_output
*.log
# BMad/blago workspace папки (не относятся к билду образа)
_blago
**/_blago
.bmad-core
.bmad-output
# Локальные секреты (на всякий случай — секреты должны идти через
# build-args / docker-compose environment, не через COPY)
.env
.env.*
!.env-example
**/.env
**/.env.*
!**/.env-example
# Артефакты других сервисов
components/desktop/.quasar
components/contracts/build
+41
View File
@@ -0,0 +1,41 @@
# Шаблон per-instance конфига. Скопируй в .env и подправь под свой инстанс.
#
# Зачем: docker-compose.yaml и boot-скрипты параметризованы — это
# позволяет держать несколько копий репо (mono-ai-1, mono-ai-2 ...) с
# полностью изолированной инфраструктурой и запускать их параллельно.
#
# Без .env compose поднимется с дефолтами (как у mono-ai-1).
# Дефолты ниже соответствуют первому инстансу — для второго и далее
# применяй смещение portов: offset = (INSTANCE_INDEX - 1) * 10.
# Индекс инстанса (1 = базовый, 2/3/... = параллельные копии).
INSTANCE_INDEX=1
# Имя docker compose проекта. Определяет префикс автогенерируемых
# имён контейнеров (mongo → <COMPOSE_PROJECT_NAME>-mongo-1).
# По умолчанию compose возьмёт имя папки — оставь как есть, если папка
# уже называется уникально (например, mono-ai-1).
COMPOSE_PROJECT_NAME=mono-ai-1
# Host-порты (для INSTANCE_INDEX=2 прибавь +10 к каждому, для =3 +20 и т.д.).
NODE_HTTP_PORT=8888
NODE_P2P_PORT=9876
NODE_HISTORY_PORT=8070
MONGO_HOST_PORT=27017
REDIS_HOST_PORT=6379
PG_HOST_PORT=5532
COOPBACK_HOST_PORT=2998
DESKTOP_HOST_PORT=2999
OPENSEARCH_HOST_PORT=9200
MINIO_HOST_PORT=9000
MINIO_CONSOLE_HOST_PORT=9001
# MinIO root credentials (только для локального dev; на prod подменяются плейбуком).
MINIO_ROOT_USER=minioadmin
MINIO_ROOT_PASSWORD=minioadmin
# URL для скриптов и кода, запускаемого с хоста (boot, networks.sh,
# preactivate.sh, health.ts). Должны соответствовать host-портам выше.
CHAIN_URL=http://127.0.0.1:8888
API_URL=http://127.0.0.1:2998/v1/graphql
MONGODB_URL=mongodb://127.0.0.1:27017
+2
View File
@@ -0,0 +1,2 @@
[core]
ignorecase = false
+3
View File
@@ -0,0 +1,3 @@
Trial run of Typecheck workflow on PR → dev.
Created 2026-05-23 to measure end-to-end duration of vue-tsc (desktop) and tsc (controller).
Do not merge; close after measurement.
+86
View File
@@ -0,0 +1,86 @@
name: Build bootstrap container
# Сборка и публикация docker-образа `dicoop/bootcoop` — bootstrap-артефакта
# для развёртывания контрактов на удалённой ноде. Образ содержит CLI
# (`pnpm run boot:remote`) и `/contracts` от dicoop/contracts (multi-stage).
# Используется как one-shot job в стороннем docker-compose рядом с
# `dicoop/blockchain` — никакой mono-инфры (mongo/postgres/desktop) не нужно.
#
# Триггер — push в dev/testnet/main. Тег `dicoop/bootcoop` совпадает с
# веткой и подтягивает соответствующий тег `dicoop/contracts` (так
# контракты и bootstrap всегда синхронны).
#
# Зависимости в hub:
# dicoop/contracts:<branch> — пакет wasm/abi (build-contracts.yaml)
#
# Образ self-contained: собирает workspace из текущего checkout'а,
# не зависит от dicoop/mono-base (который тегается только релиз-тегами).
#
# Секреты:
# DOCKERHUB_USERNAME / DOCKERHUB_TOKEN
on:
push:
branches: [dev, testnet, main]
paths:
- 'components/boot/**'
- '.github/workflows/build-bootstrap.yaml'
workflow_dispatch:
jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Determine docker tags
run: |
case "${{ github.ref_name }}" in
main)
echo "DOCKER_TAG=main" >> $GITHUB_ENV
echo "EXTRA_TAG=latest" >> $GITHUB_ENV
;;
testnet)
echo "DOCKER_TAG=testnet" >> $GITHUB_ENV
echo "EXTRA_TAG=" >> $GITHUB_ENV
;;
dev)
echo "DOCKER_TAG=dev" >> $GITHUB_ENV
echo "EXTRA_TAG=" >> $GITHUB_ENV
;;
*)
echo "Unsupported branch ${{ github.ref_name }}" >&2
exit 1
;;
esac
- name: Login to DockerHub
uses: docker/login-action@v3
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
- name: Pull contracts image
run: docker pull dicoop/contracts:${{ env.DOCKER_TAG }}
- name: Build and push image
run: |
IMAGE="dicoop/bootcoop"
docker build \
--build-arg CONTRACTS_TAG=${{ env.DOCKER_TAG }} \
--label "org.opencontainers.image.revision=${{ github.sha }}" \
--label "org.opencontainers.image.created=$(date -u +%Y-%m-%dT%H:%M:%SZ)" \
-f components/boot/Dockerfile \
-t "$IMAGE:${{ env.DOCKER_TAG }}" \
.
docker push "$IMAGE:${{ env.DOCKER_TAG }}"
if [ -n "${{ env.EXTRA_TAG }}" ]; then
docker tag "$IMAGE:${{ env.DOCKER_TAG }}" "$IMAGE:${{ env.EXTRA_TAG }}"
docker push "$IMAGE:${{ env.EXTRA_TAG }}"
fi
SHORT_SHA="${GITHUB_SHA::7}"
docker tag "$IMAGE:${{ env.DOCKER_TAG }}" "$IMAGE:${{ env.DOCKER_TAG }}-$SHORT_SHA"
docker push "$IMAGE:${{ env.DOCKER_TAG }}-$SHORT_SHA"
+462
View File
@@ -0,0 +1,462 @@
name: Release
# Единый релизный workflow по push'у тэга `v*`.
#
# Порядок (через jobs.needs):
# 1) release — контракты + контейнеры + webhook деплоя (атомарно)
# 2) publish-packages — npm publish через lerna (если не -alpha)
# 3) publish-docs — mkdocs + standards-site → gh-pages (если не -alpha + ветка main)
# 4) trigger-coopenomics — repository_dispatch в coopenomics/coopenomics (тот же гейт, что docs)
#
# Зачем последовательно: пакеты/доки/внешний триггер не должны уезжать,
# если релиз контрактов или контейнеров провалился. Раньше четыре workflow'а
# стартовали параллельно по одному тэгу — отсюда гонка из инцидента 2026-05-13
# с ledger2 walletop sweep'ом (см. историю release.yaml до объединения).
#
# Гейт `-alpha` унифицирован: пакеты + доки + триггер docs пропускают только
# не-alpha тэги. -beta/-rc/-test в проекте не используются (см. CLAUDE.md),
# поэтому проще иметь один паттерн `!contains(github.ref, '-alpha')`.
# IS_PROD в release-job остаётся на `(alpha|beta|rc|test)` — он определяет
# деплой-webhook (testnet vs production) и тэг `:latest` у образов;
# намеренно строже, чтобы случайный -rc-тэг не уехал на прод.
#
# Резолв ветки. Тэг семантики окружения не несёт (например `v2026.5.13-alpha-2`
# может лежать на testnet или dev — определяет именно ветка, на которую сделан
# merge перед тэгом). Поэтому ищем первое совпадение SHA с remote-ветками
# main/testnet/dev. branch экспортируется как outputs.branch для downstream jobs.
on:
push:
tags:
- 'v*'
permissions:
contents: write
jobs:
# Гейт TS-типов перед сборкой образов. Reusable workflow `typecheck.yaml`
# запускает vue-tsc на desktop и tsc --noEmit на controller. Нужно потому,
# что `lerna run build` в корневом Dockerfile НЕ ловит TS-ошибки:
# quasar build идёт через esbuild с выключенным vueTsc, а у controller'а
# build-скрипта вообще нет (ts-node в рантайме).
typecheck:
uses: ./.github/workflows/typecheck.yaml
release:
needs: typecheck
runs-on: ubuntu-latest
outputs:
tag_name: ${{ steps.resolve.outputs.tag_name }}
branch: ${{ steps.resolve.outputs.branch }}
is_prod: ${{ steps.resolve.outputs.is_prod }}
steps:
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0
- name: Resolve branch, build mode and tags
id: resolve
run: |
TAG_NAME="${{ github.ref_name }}"
SHA="${{ github.sha }}"
BRANCH=""
for candidate in main testnet dev; do
if git branch -r --contains "$SHA" 2>/dev/null | grep -qE "^[[:space:]]*origin/${candidate}$"; then
BRANCH="$candidate"
break
fi
done
if [ -z "$BRANCH" ]; then
echo "::error::Тэг $TAG_NAME ($SHA) не лежит ни на одной из dev/testnet/main"
exit 1
fi
case "$BRANCH" in
main)
BUILD_MODE=prod
CONTRACTS_TAG=main
CONTRACTS_EXTRA=latest
;;
testnet)
BUILD_MODE=test
CONTRACTS_TAG=testnet
CONTRACTS_EXTRA=
;;
dev)
BUILD_MODE=test
CONTRACTS_TAG=dev
CONTRACTS_EXTRA=
;;
esac
# IS_PROD определяет webhook деплоя (PRODUCTION vs TESTNET) и тэг :latest.
# Сознательно строже гейта publish-* — случайный -rc/-beta тэг не должен
# уехать на прод-вебхук, даже если в npm/docs его опубликовали.
if [[ "$TAG_NAME" =~ -(alpha|beta|rc|test) ]]; then
IS_PROD=false
WEBHOOK_URL='${{ vars.TESTNET_WEBHOOK_URL }}'
else
IS_PROD=true
WEBHOOK_URL='${{ vars.PRODUCTION_WEBHOOK_URL }}'
fi
{
echo "TAG_NAME=$TAG_NAME"
echo "SHA=$SHA"
echo "BRANCH=$BRANCH"
echo "BUILD_MODE=$BUILD_MODE"
echo "CONTRACTS_TAG=$CONTRACTS_TAG"
echo "CONTRACTS_EXTRA=$CONTRACTS_EXTRA"
echo "IS_PROD=$IS_PROD"
echo "WEBHOOK_URL=$WEBHOOK_URL"
} >> "$GITHUB_ENV"
{
echo "tag_name=$TAG_NAME"
echo "branch=$BRANCH"
echo "is_prod=$IS_PROD"
} >> "$GITHUB_OUTPUT"
echo "Release $TAG_NAME → branch=$BRANCH, build_mode=$BUILD_MODE, contracts:$CONTRACTS_TAG, prod=$IS_PROD"
- name: Login to DockerHub
uses: docker/login-action@v3
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
# === Этап 1: контракты ===
- name: Pull CDT toolchain image
run: docker pull dicoop/blockchain_v5.1.1:dev
- name: Compile contracts
working-directory: components/contracts
run: |
./build-all.sh "$BUILD_MODE"
echo "--- build/contracts ---"
ls -la build/contracts/
- name: Stage contracts docker context
working-directory: components/contracts
run: |
ROOT="docker/.context"
rm -rf "$ROOT"
mkdir -p "$ROOT/contracts"
# Имена контрактов = аргументы add_contract_build(...) только в
# незакомменченных строках (CMake-комментарий начинается с `#`).
NAMES=$(grep -E '^[[:space:]]*add_contract_build\(' CMakeLists.txt \
| sed -E 's/^[[:space:]]*add_contract_build\(([^)]*)\).*/\1/')
echo "Contracts to package:"
echo "$NAMES"
MANIFEST="$ROOT/contracts/manifest.json"
pack_one() {
local NAME="$1" WASM="$2" ABI="$3"
if [ ! -f "$WASM" ] || [ ! -f "$ABI" ]; then
echo "::warning::Skipping $NAME: artifacts missing ($WASM / $ABI)" >&2
return 1
fi
mkdir -p "$ROOT/contracts/$NAME"
cp "$WASM" "$ROOT/contracts/$NAME/$NAME.wasm"
cp "$ABI" "$ROOT/contracts/$NAME/$NAME.abi"
local SHA_WASM=$(sha256sum "$WASM" | awk '{print $1}')
local SHA_ABI=$(sha256sum "$ABI" | awk '{print $1}')
printf ' {"name":"%s","sha256_wasm":"%s","sha256_abi":"%s"}' \
"$NAME" "$SHA_WASM" "$SHA_ABI"
}
{
printf '{\n'
printf ' "build_mode": "%s",\n' "$BUILD_MODE"
printf ' "git_sha": "%s",\n' "$SHA"
printf ' "tag": "%s",\n' "$TAG_NAME"
printf ' "branch": "%s",\n' "$BRANCH"
printf ' "built_at": "%s",\n' "$(date -u +%Y-%m-%dT%H:%M:%SZ)"
printf ' "contracts": [\n'
FIRST=1
emit() {
entry=$(pack_one "$@") || return 0
[ $FIRST -eq 0 ] && printf ',\n'
FIRST=0
printf '%s' "$entry"
}
for c in $NAMES; do
if [ "$c" = "system" ]; then
# У system многоконтрактная сборка: разносим под-контракты
# eosio.* как полноценные элементы каталога, сам "system"
# как имя пропускаем.
for sub in build/contracts/system/contracts/eosio.*/; do
[ -d "$sub" ] || continue
sub_name=$(basename "$sub")
emit "$sub_name" "$sub/$sub_name.wasm" "$sub/$sub_name.abi"
done
else
emit "$c" "build/contracts/$c/$c.wasm" "build/contracts/$c/$c.abi"
fi
done
printf '\n ]\n'
printf '}\n'
} > "$MANIFEST"
cp docker/Dockerfile "$ROOT/Dockerfile"
cp docker/entrypoint.sh "$ROOT/entrypoint.sh"
chmod +x "$ROOT/entrypoint.sh"
echo "--- manifest.json ---"
cat "$MANIFEST"
- name: Build and push contracts image
working-directory: components/contracts
run: |
IMAGE="dicoop/contracts"
SHORT_SHA="${SHA::7}"
docker build \
--label "org.opencontainers.image.revision=$SHA" \
--label "org.opencontainers.image.created=$(date -u +%Y-%m-%dT%H:%M:%SZ)" \
--label "build.mode=$BUILD_MODE" \
-t "$IMAGE:$CONTRACTS_TAG" \
./docker/.context
docker push "$IMAGE:$CONTRACTS_TAG"
docker tag "$IMAGE:$CONTRACTS_TAG" "$IMAGE:$CONTRACTS_TAG-$SHORT_SHA"
docker push "$IMAGE:$CONTRACTS_TAG-$SHORT_SHA"
if [ -n "$CONTRACTS_EXTRA" ]; then
docker tag "$IMAGE:$CONTRACTS_TAG" "$IMAGE:$CONTRACTS_EXTRA"
docker push "$IMAGE:$CONTRACTS_EXTRA"
fi
- name: Verify pushed contracts image
run: |
docker run --rm "dicoop/contracts:$CONTRACTS_TAG" list
echo "---"
docker run --rm "dicoop/contracts:$CONTRACTS_TAG" sha256
# === Этап 2: контейнеры приложений ===
- name: Build and push base image
run: |
docker build --target runtime -t "dicoop/mono-base:$TAG_NAME" .
docker push "dicoop/mono-base:$TAG_NAME"
if [ "$IS_PROD" = "true" ]; then
docker tag "dicoop/mono-base:$TAG_NAME" dicoop/mono-base:latest
docker push dicoop/mono-base:latest
fi
- name: Build and push service images
run: |
build_service() {
local SVC="$1" PKG="$2" CMD="$3"
local DOCKERFILE="Dockerfile.$SVC"
{
echo "FROM dicoop/mono-base:$TAG_NAME"
echo "CMD [\"pnpm\", \"-F\", \"$PKG\", \"run\", \"$CMD\"]"
} > "$DOCKERFILE"
docker build -t "dicoop/$SVC:$TAG_NAME" -f "$DOCKERFILE" .
docker push "dicoop/$SVC:$TAG_NAME"
if [ "$IS_PROD" = "true" ]; then
docker tag "dicoop/$SVC:$TAG_NAME" "dicoop/$SVC:latest"
docker push "dicoop/$SVC:latest"
fi
}
build_service desktop '@coopenomics/desktop' start
build_service coopback '@coopenomics/controller' start
# TEMP: cooparser — пока не мигрировали потребителей на dicoop/parser
# из отдельного coopenomics/parser repo.
build_service cooparser '@coopenomics/parser' start
build_service notificator 'coop-notificator' start
build_service notifications '@coopenomics/notifications' sync
# === Этап 3: webhook деплоя ===
- name: Trigger deployment webhook
run: |
curl -X POST "$WEBHOOK_URL" \
-H 'Content-Type: application/json' \
-d "$TAG_NAME"
# ============================================================================
# publish-packages — npm publish (бывший publish-packages.yaml).
# Гейт: не-alpha. Не зависит от ветки.
# Жёстко прибиваем версию pnpm, которой сгенерён lockfile (lockfileVersion 9.0
# = pnpm 9/10). Иначе action-setup может подтянуть другую версию и переписать
# pnpm-lock.yaml → Lerna EUNCOMMIT.
# ============================================================================
publish-packages:
needs: release
if: ${{ !contains(github.ref, '-alpha') }}
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: pnpm/action-setup@v4
with:
version: 10.33.0
- uses: actions/setup-node@v4
with:
node-version: 24
registry-url: https://registry.npmjs.org
cache: pnpm
- run: pnpm install --frozen-lockfile
- run: pnpm lerna run build
- run: pnpm lerna publish from-package --yes
env:
NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}
# ============================================================================
# publish-docs — mkdocs + standards-site → gh-pages (бывший publish-docs.yaml).
# Гейт: не-alpha + ветка main.
# ВНИМАНИЕ: gh-pages step пушит на github.com/coopenomics/mono — это GitHub
# Pages. При переезде на Gitea Actions нужно будет либо подложить PAT для
# внешнего push'а в GitHub, либо переключить публикацию на Gitea Pages.
# ============================================================================
publish-docs:
needs: release
if: ${{ !contains(github.ref, '-alpha') && needs.release.outputs.branch == 'main' }}
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v4
# Версия pnpm берётся из `packageManager` корневого package.json,
# синхронно с publish-packages job'ом и Dockerfile'ами.
- name: Set up pnpm
uses: pnpm/action-setup@v4
- name: Set up Node.js
uses: actions/setup-node@v4
with:
node-version: 22
cache: pnpm
- name: Set up Python
uses: actions/setup-python@v4
with:
python-version: '3.10'
- name: Install Python requirements
run: |
python -m venv venv
source venv/bin/activate
pip install mkdocs-material mkdocs-macros-plugin mkdocs-section-index pymdown-extensions
working-directory: ./components/docs
- name: Install Node.js dependencies
run: pnpm install
working-directory: ./components/docs
- name: Patch spectaql-config.yml for CI
run: |
sed -i.bak "0,/url:.*/s|url:.*|url: 'https://testnet.coopenomics.world/backend/v1/graphql'|" spectaql-config.yml
working-directory: ./components/controller
- name: Show patched spectaql-config.yml
run: cat spectaql-config.yml
working-directory: ./components/controller
- name: Build cooptypes
run: pnpm run build
working-directory: ./components/cooptypes
- name: Generate controller docs
run: pnpm run docs
working-directory: ./components/controller
- name: Copy controller docs
run: |
mkdir -p ./components/docs/docs/graphql
cp -r ./components/controller/docs/* ./components/docs/docs/graphql/
- name: Generate sdk docs
run: pnpm run docs
working-directory: ./components/sdk
- name: Copy sdk docs
run: |
mkdir -p ./components/docs/docs/sdk
cp -r ./components/sdk/docs/* ./components/docs/docs/sdk/
- name: Generate cooptypes docs
run: pnpm run docs
working-directory: ./components/cooptypes
- name: Copy cooptypes docs
run: |
mkdir -p ./components/docs/docs/cooptypes
cp -r ./components/cooptypes/docs/* ./components/docs/docs/cooptypes/
# ── standards-site → /standards/ на docs.цифровой-кооператив.рф ──
# Отдельный Vue-сайт с BPMN-графом кооперативных стандартов,
# публикуется как поддиректория на том же домене. Vite собирает
# с base='/standards/' (см. vite.config.ts), относительные пути
# внутри dist/ и hash-router работают корректно.
# dist кладём в docs/standards/ ДО mkdocs build — так же, как
# graphql/sdk/cooptypes; mkdocs сам включит его в итоговый site/.
- name: Build standards-site
run: pnpm run build
working-directory: ./components/contracts/standards-site
- name: Copy standards-site into docs/standards
run: |
mkdir -p ./components/docs/docs/standards
cp -r ./components/contracts/standards-site/dist/* ./components/docs/docs/standards/
- name: Build docs (mkdocs)
run: |
source venv/bin/activate
mkdocs build
working-directory: ./components/docs
- name: Remove specific large file before publishing
run: |
rm -f ./components/docs/site/sdk/typedoc.json
if [ -f "./components/docs/site/sdk/typedoc.json" ]; then
echo "ERROR: typedoc.json still exists!"
exit 1
else
echo "SUCCESS: typedoc.json removed successfully"
fi
- name: Publish to GitHub Pages
run: npx gh-pages --nojekyll -d site --repo https://x-access-token:${GITHUB_TOKEN}@github.com/coopenomics/mono.git
working-directory: ./components/docs
env:
GIT_AUTHOR_NAME: github-actions
GIT_AUTHOR_EMAIL: github-actions@github.com
GIT_COMMITTER_NAME: github-actions
GIT_COMMITTER_EMAIL: github-actions@github.com
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- name: Trigger docs deployment webhook
if: ${{ success() }}
run: |
curl -X POST "${{ vars.DOCS_DEPLOY_WEBHOOK_URL }}" \
-H 'Content-Type: application/json' \
-d '{"ref":"${{ github.ref }}","sha":"${{ github.sha }}","branch":"${{ github.ref_name }}"}'
# ============================================================================
# trigger-coopenomics-docs — repository_dispatch в coopenomics/coopenomics
# (бывший build-contracts-docs.yaml). Гейт идентичен publish-docs.
# ============================================================================
trigger-coopenomics-docs:
needs: release
if: ${{ !contains(github.ref, '-alpha') && needs.release.outputs.branch == 'main' }}
runs-on: ubuntu-latest
steps:
- name: Trigger Coopenomics deployment
uses: peter-evans/repository-dispatch@v2
with:
token: ${{ secrets.COOPENOMICS_PAT }}
repository: coopenomics/coopenomics
event-type: deploy_from_mono
client-payload: '{"repository": "${{ github.repository }}", "sha": "${{ github.sha }}", "ref": "${{ github.ref }}", "actor": "${{ github.actor }}"}'
+96
View File
@@ -0,0 +1,96 @@
name: Typecheck
# Валидация TypeScript-типов для desktop (Vue 3 + Quasar) и controller (NestJS).
#
# Зачем это отдельный workflow:
# 1. `quasar build --mode ssr` в release.yaml использует Vite/esbuild и
# vue-tsc отключён через vite-plugin-checker (см. quasar.config.cjs):
# TS-ошибки в .vue/.ts НЕ ловятся при docker build образа desktop.
# 2. У `@coopenomics/controller` нет build-скрипта вовсе — `lerna run build`
# его молча пропускает; в проде `ts-node` стартует и валится на типах
# только в рантайме при загрузке модуля. Кейс PR #392 (rename 1080→1020
# в cooptypes) проскочил именно так.
#
# Триггеры:
# - pull_request на dev — гейт перед мерджем в основную ветку;
# - workflow_call — переиспользуется из release.yaml как `needs:` у release-job,
# чтобы битый тэг не уехал в DockerHub.
#
# Push в dev/testnet/main НЕ триггерит — намеренно (PR-гейт достаточен,
# а тэги покрывает workflow_call из release.yaml).
on:
pull_request:
branches: [dev]
workflow_call:
jobs:
desktop:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: pnpm/action-setup@v4
with:
version: 10.33.0
- uses: actions/setup-node@v4
with:
node-version: 22
cache: pnpm
- name: Install workspace
run: pnpm install --frozen-lockfile
# Полный lerna build по всему workspace — как в корневом Dockerfile.
# Не --scope, потому что workspace-пакеты unbuild-типа (sdk, inter,
# notifications, factory, cooptypes, …) экспортируют типы только из
# сгенерированного dist/. Без dist/ tsc/vue-tsc валятся на TS2307
# «Cannot find module». Локально это маскируется ts-node-ом, но в
# CI пути резолвятся через package.json → types → dist/.
# См. Graphiti / run #148 root cause 2026-05-23.
- name: Build all workspace packages
run: pnpm lerna run build
# quasar prepare генерирует .quasar/* (auto-imports d.ts, типы для
# quasar плагинов). Без него vue-tsc ругается на отсутствующие
# глобальные компоненты QBtn/QCard/etc.
- name: Quasar prepare
run: pnpm --filter @coopenomics/desktop run prepare
# vue-tsc проверяет и .ts, и <script lang="ts"> в .vue.
# --skipLibCheck — иначе валится на типах из транзитивных deps
# (Quasar/Vue/Vite сами по себе чистые, но в графе есть legacy).
# Из памяти: на dev-сервере висло ~час из-за конкуренции с quasar dev;
# на чистом ubuntu-latest без живого стека ожидаемо в разы быстрее.
# Если упрётся в OOM/таймаут — fallback на `pnpm typecheck`
# (tsc --noEmit --skipLibCheck без vue-tsc, без SFC шаблонов).
- name: vue-tsc (desktop)
run: pnpm --filter @coopenomics/desktop exec vue-tsc --noEmit --skipLibCheck
controller:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: pnpm/action-setup@v4
with:
version: 10.33.0
- uses: actions/setup-node@v4
with:
node-version: 22
cache: pnpm
- name: Install workspace
run: pnpm install --frozen-lockfile
# Полный lerna build по всему workspace — controller импортирует
# @coopenomics/sdk, @coopenomics/inter, @coopenomics/notifications
# помимо cooptypes/factory; их dist/ генерируется unbuild и без
# этого шага tsc валится на 37 TS2307. См. root cause выше.
- name: Build all workspace packages
run: pnpm lerna run build
- name: tsc --noEmit (controller)
run: pnpm --filter @coopenomics/controller run typecheck
+24
View File
@@ -0,0 +1,24 @@
node_modules/
lerna-debug.log
components/controller/graph.png
blockchain-data/
scripts/changelog-prompt.md
scripts/changelog-release.md
scripts/release-info.md
components/docs/docs/sdk
dist/
.env
.DS_Store
_blago/
blago/
components/reports-standarts/ВОСХОД/
# Реальные XML-образцы отчётности ПК "Восход" (ИНН 9728130611, рег.СФР 1118018397)
# могут появляться в любых подпапках reports-standarts/ — не пушим.
components/reports-standarts/**/NO_*_9728130611772801001_*.xml
components/reports-standarts/**/СФР_1118018397_*.xml
# Output files for local audit scripts (ledger2 migration)
components/contracts/cpp/ledger2/scripts/out/
.env.testnet
.pnpm-store
+7
View File
@@ -0,0 +1,7 @@
store-dir=./.pnpm-store
supported-architectures.os[]=darwin
supported-architectures.os[]=linux
supported-architectures.cpu[]=x64
supported-architectures.cpu[]=arm64
supported-architectures.libc[]=glibc
+8
View File
@@ -0,0 +1,8 @@
{
"semi": false,
"singleQuote": true,
"printWidth": 120,
"plugins": [
"prettier-plugin-sort-imports"
]
}
+7
View File
@@ -0,0 +1,7 @@
{
"recommendations": [
"vue.volar",
"vue.vscode-typescript-vue-plugin"
]
}
+74
View File
@@ -0,0 +1,74 @@
{
"editor.bracketPairColorization.enabled": true,
"editor.guides.bracketPairs": true,
"editor.tabCompletion": "onlySnippets",
"editor.defaultFormatter": "esbenp.prettier-vscode",
"eslint.run": "onType",
"eslint.validate": ["javascript", "typescript", "vue"],
"i18n-ally.localesPaths": ["src/i18n"],
"typescript.format.enable": true,
"typescript.format.indentSwitchCase": false,
"typescript.validate.enable": true,
"notebook.defaultFormatter": "Vue.volar",
// Оптимизация для монорепозитория
"typescript.preferences.useAliasesForRenames": false,
"typescript.preferences.includePackageJsonAutoImports": "on",
"typescript.suggest.autoImports": true,
"typescript.suggest.paths": true,
"typescript.updateImportsOnFileMove.enabled": "always",
"typescript.workspaceSymbols.scope": "currentProject",
// Настройки для снижения нагрузки
"files.watcherExclude": {
"**/node_modules/**": true,
"**/dist/**": true,
"**/.git/objects/**": true,
"**/.git/subtree-cache/**": true,
"**/node_modules/*/**": true,
"**/.cache/**": true,
"**/.quasar/**": true,
"**/*.tsbuildinfo": true
},
"search.exclude": {
"**/node_modules": true,
"**/dist": true,
"**/.cache": true,
"**/.quasar": true,
"**/*.tsbuildinfo": true
},
"files.exclude": {
"**/.cache": true,
"**/*.tsbuildinfo": true,
"**/node_modules/.cache": true
},
// TypeScript server настройки для монорепозитория
"typescript.tsserver.maxTsServerMemory": 8192,
"typescript.tsserver.watchOptions": {
"excludeDirectories": [
"**/node_modules",
"**/dist",
"**/.cache",
"**/.quasar",
"**/build"
]
},
// Использовать локальный TypeScript из монорепо
"typescript.tsdk": "node_modules/typescript/lib",
"typescript.enablePromptUseWorkspaceTsdk": true,
// КРИТИЧЕСКИ ВАЖНО: включить project references для монорепозитория
"typescript.tsserver.useSyntaxServer": "auto",
"typescript.tsserver.experimental.enableProjectDiagnostics": true,
// Оптимизация для больших монорепозиториев
"typescript.disableAutomaticTypeAcquisition": true,
"typescript.surveys.enabled": false,
"[typescript]": {
"editor.defaultFormatter": "vscode.typescript-language-features"
}
}
-2778
View File
File diff suppressed because it is too large Load Diff
+87
View File
@@ -0,0 +1,87 @@
# AGENTS.md
## Cursor Cloud specific instructions
### Обзор
Монорепозиторий «Цифровой Кооператив» (monocoop) — платформа управления кооперативами на блокчейне EOSIO. pnpm v9 + Lerna. Node.js v20.
### Сервисы
| Компонент | Контейнер | Порт | Описание |
|-----------|-----------|------|----------|
| controller | coopback | 2998 | NestJS GraphQL API |
| desktop | desktop | 2999 | Vue 3 + Quasar SPA |
| parser | cooparser | 4000 | Индексация блокчейна через SHiP |
| blockchain | node | 8888, 8070 | EOSIO node + State History Plugin |
| MongoDB | mongo | 27017 | Основная БД (replica set) |
| Redis | monoredis | 6379 | Кэш и стримы |
| PG | (см. compose) | 5532→5432 | Реляционная БД |
### Полный перезапуск (одна команда)
```
pnpm run reboot
```
Делает: останавливает контейнеры → чистит blockchain data и volumes → поднимает инфру → ждёт готовности → `pnpm run boot` → запускает parser и controller.
### Первоначальная настройка Cloud-окружения
1. **`/etc/hosts`** — обязательно для boot (запускается на хосте, обращается к MongoDB по docker hostname):
```
echo "127.0.0.1 mongo" | sudo tee -a /etc/hosts
echo "127.0.0.1 monoredis" | sudo tee -a /etc/hosts
```
2. **WeasyPrint** — системная зависимость для генерации PDF:
```
sudo apt-get install -y python3 python3-venv libpango-1.0-0 libcairo2 libffi-dev libjpeg-dev libopenjp2-7-dev libharfbuzz-dev
sudo python3 -m venv /opt/weasyprint-venv && sudo /opt/weasyprint-venv/bin/pip install WeasyPrint==67
sudo ln -sf /opt/weasyprint-venv/bin/weasyprint /usr/local/bin/weasyprint
```
3. **Контракты** (test-режим — позволяет boot с 1 членом совета):
```
cd components/contracts && sudo rm -rf build && bash build-all.sh test
```
4. **Shared-библиотеки** (порядок важен):
```
pnpm --filter cooptypes run build
pnpm --filter @coopenomics/factory run build
pnpm --filter @coopenomics/sdk run build
pnpm --filter @coopenomics/notifications run build
```
5. **`.env` файлы** — скопировать из `.env-example`, адаптировать hostnames:
- Controller/Parser (в Docker): хосты по именам контейнеров из docker-compose (порт БД 5432)
- Boot (на хосте): `127.0.0.1`, PG порт `5532`, mongo через `/etc/hosts`
- Desktop: `127.0.0.1`
- Controller: `BACKEND_URL` (публичный URL API) и `FRONTEND_URL` (публичный URL SPA), см. `components/controller/.env-example`
- **CHAIN_ID**: берётся из `curl http://localhost:8888/v1/chain/get_info` после старта ноды
- Controller требует `VAPID_PUBLIC_KEY` и `VAPID_PRIVATE_KEY`
6. **Запуск**: `pnpm run reboot`, затем `docker compose up -d --force-recreate coopback cooparser` (если .env менялись)
### Запуск тестов
- **Factory** (`components/factory`): нужен только MongoDB. Запуск:
```
NODE_ENV=test SOURCE=local MONGO_URI=$MONGO_URI SKIP_BLOCK_FETCH=TRUE pnpm --filter @coopenomics/factory test
```
`MONGO_URI` по умолчанию: `mongodb://<host>:27017/cooperative-x`.
- **Boot** (`components/boot`): требует полный EOSIO blockchain + MongoDB + PG. Запуск после `pnpm run reboot`:
```
pnpm --filter @coopenomics/boot test
```
- **Duplicate transaction** — в boot-тестах EOSIO отклоняет транзакции с одинаковым хешем (TAPOS block + action data). При повторном вызове `refreshSegment` для того же участника — добавить `await sleep(500)` перед ним. Паттерн уже используется (см. комментарий на строке ~720 capital.test.ts).
### Критические gotchas
- **SHiP порт 8070** — `state-history-endpoint = 0.0.0.0:8070` в config.ini. Парсер: `SHIP=ws://node:8070`.
- **Парсер START_BLOCK**: при `START_BLOCK=1` на чистой БД стартует с HEAD и делает частичную инициализацию. Для полного replay: временно `START_BLOCK=2`, после первого запуска вернуть `1`.
- **SSR desktop в dev** — расширения не рендерятся из-за Pinia SSR-сериализации компонентов. Dev — SPA (`quasar dev`), production build SSR работает.
- **Тестовые учётные данные**: email `ivanov@example.com`, ключ — дефолтный EOSIO dev key (см. `components/boot/.env-example`), пользователь `ant` (председатель).
- **Docker hostnames**: без `network_mode: host` — контейнеры обращаются друг к другу по именам контейнеров из docker-compose.
- **Установка пакетов**: только через фильтр — `pnpm add <pkg> --filter <component>`.
+566
View File
@@ -0,0 +1,566 @@
# v2026.4.2-2
В этом релизе — стабилизация Благороста для вывода в продуктивную работу с результатами интеллектуальной деятельности. Отдельно заложена основа под отчётность в ФНС и ФСС и прототип поиска по документам.
**Благорост и проекты**
- Быстрые действия на странице программы: создать проект, компонент, задачу или требование.
- Требования к компонентам в репозитории: поддержка **Mermaid**, **Draw.io** и **BPMN**.
- Синхронизация проектов, компонентов, требований и задач с Git-репозиторием результатов.
- Встраивание полноразмерного видео (iframe) на страницах проектов.
- Скачивание пакета подписанных документов одной кнопкой.
- Комнаты проектов в кооперативном мессенджере.
**Мессенджер и звонки**
- Автосекретарь: запись синхронных звонков, текстовых и голосовых сообщений в проектных комнатах.
**Отчётность и инфраструктура**
- Прототип фабрики отчётов ФНС/ФСС: выгрузка в XML для дальнейшей отправки.
- Прототип поисковой системы по документам.
- Установщик для развёртывания на своих серверах (разработка или эксплуатация).
- Рефакторинг в сторону чистой архитектуры на бэкенде.
- Ускорение сборки фронтенда за счёт перехода на **Vite 8**.
**Исправления**
- Повторное общее собрание больше не мешало завершить онбординг кооператива.
- Центр уведомлений не блокировал загрузку рабочего стола при отключённом провайдере оповещений.
- Уведомления о собрании совета по свободным вопросам снова доходят до членов совета.
- В интерфейсе восстановлено отображение контактов кооператива.
#releases
---
# v2026.4.2-2
В этом релизе — стабилизация Благороста для вывода в продуктивную работу с результатами интеллектуальной деятельности. Отдельно заложена основа под отчётность в ФНС и ФСС и прототип поиска по документам.
**Благорост и проекты**
- Быстрые действия на странице программы: создать проект, компонент, задачу или требование.
- Требования к компонентам в репозитории: поддержка **Mermaid**, **Draw.io** и **BPMN**.
- Синхронизация проектов, компонентов, требований и задач с Git-репозиторием результатов.
- Встраивание полноразмерного видео (iframe) на страницах проектов.
- Скачивание пакета подписанных документов одной кнопкой.
- Комнаты проектов в кооперативном мессенджере.
**Мессенджер и звонки**
- Автосекретарь: запись синхронных звонков, текстовых и голосовых сообщений в проектных комнатах.
**Отчётность и инфраструктура**
- Прототип фабрики отчётов ФНС/ФСС: выгрузка в XML для дальнейшей отправки.
- Прототип поисковой системы по документам.
- Установщик для развёртывания на своих серверах (разработка или эксплуатация).
- Рефакторинг в сторону чистой архитектуры на бэкенде.
- Ускорение сборки фронтенда за счёт перехода на **Vite 8**.
**Исправления**
- Повторное общее собрание больше не мешало завершить онбординг кооператива.
- Центр уведомлений не блокировал загрузку рабочего стола при отключённом провайдере оповещений.
- Уведомления о собрании совета по свободным вопросам снова доходят до членов совета.
- В интерфейсе восстановлено отображение контактов кооператива.
#releases
---
# v2025.12.28-8
В этой версии представлен прототип трекера результатов интеллектуальной деятельности, реализован мост в 1С, обновлен интерфейс и существенно повышена стабильность системы.
---
### ✨ Новые функции
- [#332](https://github.com/coopenomics/mono/issues/332): Прототип конструктора требований дополнительных документов при регистрации
- [#330](https://github.com/coopenomics/mono/issues/330): Прототип моста в 1С:Бухгалтерию для передачи документов и проводок
- [#329](https://github.com/coopenomics/mono/issues/329): Интеграция и тестирование LMS TUTOR для образовательных задач
- [#328](https://github.com/coopenomics/mono/issues/328): Размещение прототипов мульти-лендингов на цифровой-кооператив.рф и coopenomics.world
- [#326](https://github.com/coopenomics/mono/issues/326): Минимальный интерфейс трекера результатов интеллектуальной деятельности
- [#324](https://github.com/coopenomics/mono/issues/324): Смарт-контракт генерации и капитализации результатов интеллектуальной деятельности ("Благорост")
- [#322](https://github.com/coopenomics/mono/issues/322): Поставка обновлений ПО с нулевым даунтаймом по blue-green стратегии
- [#321](https://github.com/coopenomics/mono/issues/321): Внедрение системы проводок по фондам для контрактов
- [#319](https://github.com/coopenomics/mono/issues/319): Палитра команд и быстрый доступ к страницам рабочих столов (cmk+k)
- [#316](https://github.com/coopenomics/mono/issues/316): Переход рабочего стола на GraphQL SDK
- [#314](https://github.com/coopenomics/mono/issues/314): Развёртывание GlitchTip для мониторинга ошибок
- [#306](https://github.com/coopenomics/mono/issues/306): Модуль запросов и мутаций для контракта капитализации
### 🐛 Исправления ошибок
- [#312](https://github.com/coopenomics/mono/issues/312): Исправление подписки на изменение статуса коммитов
- [#309](https://github.com/coopenomics/mono/issues/309): Исправление отображения чужих билетов времени в трекере
### 🔧 Улучшения
- [#331](https://github.com/coopenomics/mono/issues/331): Настройка системы мониторинга сбоев и ошибок на базе GlitchTIP, Loki, Prometheus
- [#327](https://github.com/coopenomics/mono/issues/327): Пользовательская документация по интерфейсам цифрового кооператива
- [#325](https://github.com/coopenomics/mono/issues/325): Документирование смарт-контракта программы "Благорост"
- [#308](https://github.com/coopenomics/mono/issues/308): Улучшение отображения рабочих столов в магазине приложений
- [#307](https://github.com/coopenomics/mono/issues/307): Объединение настроек контракта с нативными настройками приложения
- [#305](https://github.com/coopenomics/mono/issues/305): Объединение полей title и description в проекте
- [#304](https://github.com/coopenomics/mono/issues/304): Доменная модель контракта капитализации на бэкенде
- [#303](https://github.com/coopenomics/mono/issues/303): Пересмотр архитектуры парсера и формирования локальной истории
- [#302](https://github.com/coopenomics/mono/issues/302): Рефакторинг архитектуры, внедрение двухконтурной шины данных и обработки микрофорков
- [#301](https://github.com/coopenomics/mono/issues/301): Доработка и отладка контракта "Капитализация РИД" v0.2
- [#222](https://github.com/coopenomics/mono/issues/222): Внедрение метода Водянова для распределения пула премий по программе "Благорост"
- [#212](https://github.com/coopenomics/mono/issues/212): Снижение точности валютных значений до двух знаков после запятой в документах
#releases
---
# v2025.12.28
В этой версии представлен прототип трекера результатов интеллектуальной деятельности, реализован мост в 1С, обновлен интерфейс и существенно повышена стабильность системы.
---
### ✨ Новые функции
- [#332](https://github.com/coopenomics/mono/issues/332): Прототип конструктора требований дополнительных документов при регистрации
- [#330](https://github.com/coopenomics/mono/issues/330): Прототип моста в 1С:Бухгалтерию для передачи документов и проводок
- [#329](https://github.com/coopenomics/mono/issues/329): Интеграция и тестирование LMS TUTOR для образовательных задач
- [#328](https://github.com/coopenomics/mono/issues/328): Размещение прототипов мульти-лендингов на цифровой-кооператив.рф и coopenomics.world
- [#326](https://github.com/coopenomics/mono/issues/326): Минимальный интерфейс трекера результатов интеллектуальной деятельности
- [#324](https://github.com/coopenomics/mono/issues/324): Смарт-контракт генерации и капитализации результатов интеллектуальной деятельности ("Благорост")
- [#322](https://github.com/coopenomics/mono/issues/322): Поставка обновлений ПО с нулевым даунтаймом по blue-green стратегии
- [#321](https://github.com/coopenomics/mono/issues/321): Внедрение системы проводок по фондам для контрактов
- [#319](https://github.com/coopenomics/mono/issues/319): Палитра команд и быстрый доступ к страницам рабочих столов (cmk+k)
- [#316](https://github.com/coopenomics/mono/issues/316): Переход рабочего стола на GraphQL SDK
- [#314](https://github.com/coopenomics/mono/issues/314): Развёртывание GlitchTip для мониторинга ошибок
- [#306](https://github.com/coopenomics/mono/issues/306): Модуль запросов и мутаций для контракта капитализации
### 🐛 Исправления ошибок
- [#312](https://github.com/coopenomics/mono/issues/312): Исправление подписки на изменение статуса коммитов
- [#309](https://github.com/coopenomics/mono/issues/309): Исправление отображения чужих билетов времени в трекере
### 🔧 Улучшения
- [#331](https://github.com/coopenomics/mono/issues/331): Настройка системы мониторинга сбоев и ошибок на базе GlitchTIP, Loki, Prometheus
- [#327](https://github.com/coopenomics/mono/issues/327): Пользовательская документация по интерфейсам цифрового кооператива
- [#325](https://github.com/coopenomics/mono/issues/325): Документирование смарт-контракта программы "Благорост"
- [#308](https://github.com/coopenomics/mono/issues/308): Улучшение отображения рабочих столов в магазине приложений
- [#307](https://github.com/coopenomics/mono/issues/307): Объединение настроек контракта с нативными настройками приложения
- [#305](https://github.com/coopenomics/mono/issues/305): Объединение полей title и description в проекте
- [#304](https://github.com/coopenomics/mono/issues/304): Доменная модель контракта капитализации на бэкенде
- [#303](https://github.com/coopenomics/mono/issues/303): Пересмотр архитектуры парсера и формирования локальной истории
- [#302](https://github.com/coopenomics/mono/issues/302): Рефакторинг архитектуры, внедрение двухконтурной шины данных и обработки микрофорков
- [#301](https://github.com/coopenomics/mono/issues/301): Доработка и отладка контракта "Капитализация РИД" v0.2
- [#222](https://github.com/coopenomics/mono/issues/222): Внедрение метода Водянова для распределения пула премий по программе "Благорост"
- [#212](https://github.com/coopenomics/mono/issues/212): Снижение точности валютных значений до двух знаков после запятой в документах
#releases
---
# v2025.12.28
В этом релизе реализован смарт-контракт генерации и капитализации результатов интеллектуальной деятельности, завершена интеграция с учётными системами, улучшены интерфейсы и документация. Подробнее о контракте: https://coopenomics.world/contracts/group__public__capital.html
✨ Новые функции
- [#324](https://github.com/coopenomics/mono/issues/324): Реализован смарт-контракт генерации и капитализации результатов интеллектуальной деятельности ("Благорост")
- [#301](https://github.com/coopenomics/mono/issues/301): Контракт "Капитализация РИД" v0.2
- [#330](https://github.com/coopenomics/mono/issues/330): Прототип моста в 1С:Бухгалтерию: выгрузка документов и проводки по счетам
- [#322](https://github.com/coopenomics/mono/issues/322): Обновления ПО с нулевым даунтаймом по blue-green стратегии
- [#319](https://github.com/coopenomics/mono/issues/319): Палитра команд и быстрый доступ к страницам рабочих столов (cmk+k)
- [#308](https://github.com/coopenomics/mono/issues/308): Магазин приложений с поддержкой подключения нескольких рабочих столов одним приложением
- [#326](https://github.com/coopenomics/mono/issues/326): Минимальный интерфейс трекера результатов интеллектуальной деятельности по программе "Благорост"
- [#332](https://github.com/coopenomics/mono/issues/332): Прототип конструктора требований дополнительных документов при регистрации
🐛 Исправления ошибок
- [#312](https://github.com/coopenomics/mono/issues/312): Исправлена ошибка со статусом коммитов — подписка теперь работает корректно
- [#309](https://github.com/coopenomics/mono/issues/309): Исправлен баг с отображением чужих билетов времени в трекере
🔧 Улучшения
- [#325](https://github.com/coopenomics/mono/issues/325): Документирован смарт-контракт программы "Благорост"
- [#327](https://github.com/coopenomics/mono/issues/327): Подготовлена пользовательская документация цифрового кооператива по интерфейсам
- [#329](https://github.com/coopenomics/mono/issues/329): Интеграция и тестирование образовательной платформы LMS TUTOR на Wordpress
- [#328](https://github.com/coopenomics/mono/issues/328): Размещены прототипы мульти-лендингов на цифровой-кооператив.рф и coopenomics.world
- [#321](https://github.com/coopenomics/mono/issues/321): Встроена система проводок по фондам и интеграция с контрактами
- [#318](https://github.com/coopenomics/mono/issues/318): Настроены Loki & Grafana для выгрузки логов из контейнеров
- [#316](https://github.com/coopenomics/mono/issues/316): Завершён переход рабочего стола на GraphQL SDK
- [#314](https://github.com/coopenomics/mono/issues/314): Развёрнут GlitchTip как альтернатива Sentry
- [#307](https://github.com/coopenomics/mono/issues/307): Интеграция настроек контракта с нативными настройками приложения, поддержка импорта после конфигурации
- [#306](https://github.com/coopenomics/mono/issues/306): Собран модуль запросов и мутаций контракта капитализации
- [#305](https://github.com/coopenomics/mono/issues/305): Упрощена структура проекта — title & description объединены в одно поле
- [#304](https://github.com/coopenomics/mono/issues/304): Реализована доменная модель контракта капитализации на бэкенде с поддержкой микрофорков
- [#303](https://github.com/coopenomics/mono/issues/303): Пересмотрена архитектура парсера и формирования локальной истории
- [#302](https://github.com/coopenomics/mono/issues/302): Рефакторинг архитектуры, реализована двухконтурная шина данных и обработка микрофорков
- [#212](https://github.com/coopenomics/mono/issues/212): Уменьшена точность валютных значений в документах с четырёх до двух знаков
#releases
---
# v2025.9.1
В системе Кооперативной Экономики развернут смарт-контракт CAPITAL v0.2 для генерации и капитализации результатов интеллектуальной деятельности. Контракт описывает и обеспечивает:
- бизнес-процесс производства результатов интеллектуальной деятельности в кооперативах создателями, авторами, инвесторами, координаторами, мастерами и собственниками имущества в кооперации на проектах;
- приём результатов интеллектуальной деятельности в качестве паевых взносов в кооператив;
- распределение потока членских взносов среди вкладчиков;
- капитализацию результатов интеллектуальной деятельности новыми результатами по модели золотого сечения;
- оценку вкладов авторов и создателей по методу Водянова;
В основе математической модели контракта лежит принцип распределения справедливой выгоды между вкладчиками согласно концепции "Общественно-полезного времени", разработанной в рамках теорий Кузнецова и академика Глушкова при работе над проектом общегосударственной автоматизированной системы учета и обработки информации (ОГАС).
Подробнее в документации: https://coopenomics.world/contracts/group__public__capital.html
✨ Новые функции
- [#301](https://github.com/coopenomics/mono/issues/301): Реализация контракта "Капитализация" v0.2: регистрация вкладчиков, создание и управление проектами, поддержка инвестиций, ссуд, членских взносов, проведение голосований, расчет капитализации, интеграция с внешними контрактами, поддержка импорта данных.
#releases
---
# v2025.7.1-1
В этом релизе реализованы механизмы возврата паевого взноса пайщика и инструменты управления этим процессом для членов совета. Также внесены визуальные доработки интерфейсов для улучшения восприятия информации.
✨ Новые функции
- [#276](https://github.com/coopenomics/mono/issues/276): Реализовать путь возврата паевого взноса из кошелька пайщика
- [#281](https://github.com/coopenomics/mono/issues/281): Генерация заявления на возврат паевого взноса
- [#282](https://github.com/coopenomics/mono/issues/282): Генерация решения совета на возврат паевого взноса
- [#278](https://github.com/coopenomics/mono/issues/278): Введение методов управления возвратами паевых взносов в контроллере
- [#279](https://github.com/coopenomics/mono/issues/279): Отобразить исходящие платежи с кнопками управления в реестре платежей для совета
🐛 Исправления ошибок
- [#286](https://github.com/coopenomics/mono/issues/286): Поправить ошибки склонений времени
- [#262](https://github.com/coopenomics/mono/issues/262): Баг: рабочий стол совета включается, однако, страница всегда открывается со стола пайщика
- [#261](https://github.com/coopenomics/mono/issues/261): Баг: первая загрузка переадресует на главную страницу всегда - прямой переход на собрание становится недоступен.
🔧 Улучшения
- [#285](https://github.com/coopenomics/mono/issues/285): Корректировка дизайна кошелька, профиля, повестки совета, реестра документов, реестра платежей
- [#284](https://github.com/coopenomics/mono/issues/284): Разместить кошелек на главную вместо профиля
- [#283](https://github.com/coopenomics/mono/issues/283): Ввести лоадер на переходе между рабочими столами
- [#280](https://github.com/coopenomics/mono/issues/280): Мигрировать имеющиеся данные о входящих платежах в новую модель
- [#277](https://github.com/coopenomics/mono/issues/277): Рефакторинг модуля платежей: переход на унифицированную модель входящего и исходящего платежа
#releases
---
# v2025.6.14
Разработан модуль для проведения очередных общих собраний пайщиков. Исправлены баги, внесены улучшения пользовательского интерфейса.
✨ Новые функции
- [#264](https://github.com/coopenomics/mono/issues/264): Разработан смарт-контракт общего собрания пайщиков (meet)
- [#263](https://github.com/coopenomics/mono/issues/263): Реализован модуль оповещений на электронные почты по жизненному циклу общего собрания пайщиков
- [#273](https://github.com/coopenomics/mono/issues/273): Встроены реальные шаблоны документов общего собрания
- [#268](https://github.com/coopenomics/mono/issues/268): Добавлена страница результатов общего собрания
- [#267](https://github.com/coopenomics/mono/issues/267): Добавлена страница просмотра и скачивания бюллетеней и уведомлений по собранию
- [#270](https://github.com/coopenomics/mono/issues/270): Ссылка в оповещении ведет на страницу собрания с документом-уведомлением для подписи
🐛 Исправления ошибок
- [#262](https://github.com/coopenomics/mono/issues/262): Исправлено некорректное открытие рабочего стола совета
- [#261](https://github.com/coopenomics/mono/issues/261): Исправлена ошибка с редиректом при первой загрузке и прямом переходе на собрание
- [#259](https://github.com/coopenomics/mono/issues/259): Исправлены отступы в мобильной карточке пайщика
- [#258](https://github.com/coopenomics/mono/issues/258): Убран hover-эффект на документе и пайщике в таблице
🔧 Улучшения
- [#274](https://github.com/coopenomics/mono/issues/274): Настроена рассылка оповещений на почту при получении решения о проведении собрания
- [#272](https://github.com/coopenomics/mono/issues/272): Подписанные уведомления сохраняются и извлекаются из реестра по Graph-QL
- [#271](https://github.com/coopenomics/mono/issues/271): Ведется подсчет количества пайщиков в каждом кооперативе при добавлении и удалении
- [#260](https://github.com/coopenomics/mono/issues/260): Введен счетчик количества пайщиков в кооперативе на контракте регистратора
- [#256](https://github.com/coopenomics/mono/issues/256): Отображается статус членства каждого пайщика
- [#255](https://github.com/coopenomics/mono/issues/255): В разделе Платежи отображается ФИО/Наименование плательщика
- [#269](https://github.com/coopenomics/mono/issues/269): Реализована рассылка уведомлений перед началом собрания
- [#265](https://github.com/coopenomics/mono/issues/265): Проведена отладка и тестирование процесса общего собрания пайщиков
- [#266](https://github.com/coopenomics/mono/issues/266): Протестированы все процессы общего собрания
#releases
---
# v2025.5.14
В этом релизе реализован новый стандарт передачи и хранения документов по блокчейну с поддержкой неограниченного количества подписей и их валидацией. Также внесены улучшения в интерфейс и исправлены ошибки.
✨ Новые функции
- [#252](https://github.com/coopenomics/mono/issues/252): Внедрение обновленного стандарта хранения и передачи документов по блокчейну
- [#251](https://github.com/coopenomics/mono/issues/251): Реализация версионированного мигратора данных для контроллера кооператива
- [#244](https://github.com/coopenomics/mono/issues/244): Обновление стандарта сборки документов и переход на хэш-идентификаторы
🐛 Исправления ошибок
- [#249](https://github.com/coopenomics/mono/issues/249): Исправлена спутанная маршрутизация между рабочими столами кооперативов
- [#253](https://github.com/coopenomics/mono/issues/253): Исправлена избыточная точность суммы оплаты в заявлении на вступление
🔧 Улучшения
- [#259](https://github.com/coopenomics/mono/issues/259): Исправлены отступы в мобильной карточке пайщика на странице пайщиков
- [#258](https://github.com/coopenomics/mono/issues/258): Удалён hover-эффект для документов и пайщиков в таблице
- [#257](https://github.com/coopenomics/mono/issues/257): Добавлено сохранение светлой/тёмной темы в localStorage и восстановление при загрузке страницы
- [#256](https://github.com/coopenomics/mono/issues/256): Отображение статуса членства каждого пайщика в разделе "Пайщики"
- [#255](https://github.com/coopenomics/mono/issues/255): Отображение ФИО/Наименования плательщика в разделе "Платежи"
#releases
---
# v2025.5.2
В этом релизе рабочие столы переведены на серверный рендеринг, что улучшает стабильность развертывания и упрощает автоматизацию поставки ПО. Данный релиз является подготовительным к переходу на новый стандарт цифровых документов на платформе.
✨ Новые функции
- [#245](https://github.com/coopenomics/mono/issues/245): Перевод десктопа на серверный рендеринг с поддержкой динамических переменных окружения
🐛 Исправления ошибок
- [#247](https://github.com/coopenomics/mono/issues/247): Исправлен баг с повторной поставкой ПО при обрывах соединения между серверами
🔧 Улучшения
- [#246](https://github.com/coopenomics/mono/issues/246): Перевод CI/CD на сборку и поставку предсобранных докер-контейнеров
#releases
---
# MONO v2025.4.29
В этом релизе реализована новая архитектура рабочих столов с установкой через маркетплейс. Добавлены стол пайщика и стол совета, переработаны разделы документов и подписей, улучшено разделение кошелька и профиля для повышения удобства пользователей.
✨ Новые функции
- [#234](https://github.com/coopenomics/mono/issues/234): Маркетплейс рабочих столов с поддержкой разных ролей и микросервисной архитектурой
- [#238](https://github.com/coopenomics/mono/issues/238): Контроллер общего собрания пайщиков с поддержкой документооборота и подписей
- [#233](https://github.com/coopenomics/mono/issues/233): Минимальный смарт-контракт общих собраний пайщиков
- [#232](https://github.com/coopenomics/mono/issues/232): Бэкенд полного обозревателя блоков
🐛 Исправления ошибок
- [#231](https://github.com/coopenomics/mono/issues/231): Исправления ошибок регистрации, выхода из системы, отображения платежей и редактирования организации
🔧 Улучшения
- [#243](https://github.com/coopenomics/mono/issues/243): Контроль прав доступа на получении документов пайщика
- [#242](https://github.com/coopenomics/mono/issues/242): Бесконечный скролл на документах пайщика и кооператива
- [#241](https://github.com/coopenomics/mono/issues/241): Раздел "Документы" для пайщика
- [#240](https://github.com/coopenomics/mono/issues/240): Множественные подписи на одном документе
- [#239](https://github.com/coopenomics/mono/issues/239): Последовательные методы подписи протокола общего собрания
- [#237](https://github.com/coopenomics/mono/issues/237): Мобильная вёрстка на страницах стола совета
- [#236](https://github.com/coopenomics/mono/issues/236): Пересобран лендинг для MONO
- [#235](https://github.com/coopenomics/mono/issues/235): Настроен флоу гитхаб-релизов с описаниями
- [#226](https://github.com/coopenomics/mono/issues/226): Встроено редактирование пайщиков
- [#224](https://github.com/coopenomics/mono/issues/224): Добавлено ТЗ по контракту капитализации
---
# Change Log
All notable changes to this project will be documented in this file.
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
## [2.2.10](https://github.com/coopenomics/mono/compare/v2.2.9...v2.2.10) (2025-03-27)
### Bug Fixes
* add Zeus type ([7bcb6e3](https://github.com/coopenomics/mono/commit/7bcb6e30a77b0ab89c5293188b58f08f19c8761e))
## [2.2.9](https://github.com/coopenomics/mono/compare/v2.2.8...v2.2.9) (2025-03-12)
**Note:** Version bump only for package monocoop
## [2.2.8](https://github.com/coopenomics/monocoop/compare/v2.2.7...v2.2.8) (2025-02-10)
**Note:** Version bump only for package monocoop
## [2.2.7](https://github.com/coopenomics/monocoop/compare/v2.2.6...v2.2.7) (2025-02-07)
**Note:** Version bump only for package monocoop
## [2.2.6](https://github.com/coopenomics/monocoop/compare/v2.2.6-alpha.0...v2.2.6) (2025-01-27)
**Note:** Version bump only for package monocoop
## [2.2.5](https://github.com/coopenomics/monocoop/compare/v2.2.4...v2.2.5) (2025-01-18)
**Note:** Version bump only for package monocoop
## [2.2.4](https://github.com/coopenomics/monocoop/compare/v2.2.0...v2.2.4) (2025-01-17)
**Note:** Version bump only for package monocoop
## [2.2.3](https://github.com/coopenomics/monocoop/compare/v2.2.0...v2.2.3) (2025-01-16)
**Note:** Version bump only for package monocoop
## [2.2.1](https://github.com/coopenomics/monocoop/compare/v2.2.0...v2.2.1) (2025-01-14)
**Note:** Version bump only for package monocoop
## [2.1.9](https://github.com/coopenomics/monocoop/compare/v2.1.8...v2.1.9) (2025-01-14)
**Note:** Version bump only for package monocoop
## [2.1.8](https://github.com/coopenomics/monocoop/compare/v2.1.6...v2.1.8) (2024-12-24)
**Note:** Version bump only for package monocoop
## [2.1.7](https://github.com/coopenomics/monocoop/compare/v2.1.6...v2.1.7) (2024-12-03)
**Note:** Version bump only for package monocoop
## [2.1.6](https://github.com/coopenomics/monocoop/compare/v2.1.5...v2.1.6) (2024-10-30)
**Note:** Version bump only for package monocoop
## [2.1.5](https://github.com/coopenomics/monocoop/compare/v2.1.4...v2.1.5) (2024-10-28)
**Note:** Version bump only for package monocoop
## [2.1.4](https://github.com/coopenomics/monocoop/compare/v2.1.4-alpha.2...v2.1.4) (2024-10-28)
**Note:** Version bump only for package monocoop
## [2.1.3](https://github.com/coopenomics/monocoop/compare/v2.1.2-alpha.10...v2.1.3) (2024-10-26)
## [2.1.2](https://github.com/coopenomics/monocoop/compare/v2.1.1...v2.1.2) (2024-10-19)
**Note:** Version bump only for package monocoop
## [2.1.2](https://github.com/coopenomics/monocoop/compare/v2.1.1...v2.1.2) (2024-10-19)
**Note:** Version bump only for package monocoop
# [2.1.0](https://github.com/coopenomics/monocoop/compare/v2.0.10-alpha.3...v2.1.0) (2024-10-13)
### Features
* запрос соглашений ([9a6a72f](https://github.com/coopenomics/monocoop/commit/9a6a72f605ba52eef2ed6f18ccee6fbed287ea00))
## [2.0.9](https://github.com/coopenomics/monocoop/compare/v2.0.8...v2.0.9) (2024-10-10)
**Note:** Version bump only for package monocoop
## [2.0.8](https://github.com/coopenomics/monocoop/compare/v2.0.7...v2.0.8) (2024-10-09)
**Note:** Version bump only for package monocoop
## [2.0.7](https://github.com/coopenomics/monocoop/compare/v2.0.6...v2.0.7) (2024-09-30)
**Note:** Version bump only for package monocoop
## [2.0.6](https://github.com/coopenomics/monocoop/compare/v2.0.5...v2.0.6) (2024-09-30)
**Note:** Version bump only for package monocoop
## [2.0.5](https://github.com/coopenomics/monocoop/compare/v2.0.5-alpha.0...v2.0.5) (2024-09-30)
**Note:** Version bump only for package monocoop
## [2.0.2](https://github.com/coopenomics/monocoop/compare/v2.0.2-alpha.1...v2.0.2) (2024-09-29)
**Note:** Version bump only for package monocoop
# 2.1.0 (2024-09-29)
### Bug Fixes
* **importers:** исправлена ошибка в импорте модуля @wharfkit/contract ([bf89032](https://github.com/coopenomics/monocoop/commit/bf89032d8f66444804a2521f4eb96ffc75b0f605))
* **terminal:** исправлен шрифт в README ([889447a](https://github.com/coopenomics/monocoop/commit/889447a93ceadb577613ddb5b1cb2ef1cc3d54b6))
* **terminal:** исправлено описание проекта ([989b318](https://github.com/coopenomics/monocoop/commit/989b3180ded99a871e018cf26e6c493449223c01))
* **terminal:** fix typo in README.md ([fdf9996](https://github.com/coopenomics/monocoop/commit/fdf999619d2d69e960b062fe6815f5b057c95f48))
### Features
* добавлен docker-compose.yaml ([6a46697](https://github.com/coopenomics/monocoop/commit/6a46697c9d6cc3cde14dbce8f70997c00f9850de))
* **package:** добавлен скрипт gpt-commit для удобного коммита ([e0b5107](https://github.com/coopenomics/monocoop/commit/e0b510799bb0ac68890d572deb652beefd0651c4))
* **terminal:** добавлена поддержка новых команд ([73e4ca2](https://github.com/coopenomics/monocoop/commit/73e4ca226acebcbea3ae59a62def99d86efb1353))
+301
View File
@@ -0,0 +1,301 @@
# mono (coopenomics/mono) — рабочие заметки
Этот файл — общая память агента для пяти чекаутов: `~/mono-ai-1`..`~/mono-ai-5`. Реальный файл лежит в `mono-ai-1/CLAUDE.md`, остальные четыре — симлинки сюда; правки коммитим из mono-ai-1 в ветку `dev`.
## Стек монорепы
| Слой | Где | Технология |
|------|-----|------------|
| Backend (coopback) | `components/controller/` | NestJS 10, TypeScript, TypeORM, GraphQL, EventEmitter2 |
| Frontend (UI пайщика) | **`components/desktop/`** | **Vue 3 + Quasar** в SSR-режиме (`quasar dev --mode ssr`) |
| Контракты | `components/contracts/` | EOSIO/CDT, C++ |
| SDK для frontend | `components/sdk/` | TypeScript, авто-генерится из controller GraphQL schema |
| Parser blockchain | `components/parser/` | TypeScript |
| Boot/orchestration | `components/boot/` | TypeScript |
**Frontend (`components/desktop/`) — FSD структура:** `src/{app,pages,processes,widgets,features,entities,shared,stores,desktops,boot}/`.
Когда план говорит «UI компонент» / «frontend integration» — путь `components/desktop/src/{features|widgets|pages|processes}/<name>/`, расширение `.vue` (composition API + `<script setup lang="ts">`), стили Quasar (QChip/QBtn/QCard/QDialog…), GraphQL через Apollo Client + сгенерированные типы из `components/sdk/`. Dev — `pnpm --filter @coopenomics/desktop run dev` или `devnet` (без SSR).
**НЕ путать:** НЕТ `components/app-cooperative/` — не предлагать. Все frontend-сессии работают в той же монорепе, что и backend. В стеке **никакого React нигде нет**.
## Worktree-политика
**Для mono-ai-4 (базовая ветка `marketplace2`, Стол заказов):** **worktree приветствуется** — изоляция работ + параллельные ветки. Если worktree пуст от `node_modules` и `.env` (pnpm их не дублирует):
```bash
WT=/home/admin/mono-ai-4/.claude/worktrees/<name>
ln -s /home/admin/mono-ai-4/node_modules $WT/node_modules
ln -s /home/admin/mono-ai-4/components/controller/node_modules $WT/components/controller/node_modules
ln -s /home/admin/mono-ai-4/components/controller/.env $WT/components/controller/.env
```
Аналогично для других пакетов, чьи тесты будут запускаться (`components/desktop/node_modules`, `components/sdk/node_modules`). `jest` из bin: `cd $WT/components/controller && ./node_modules/.bin/jest -i <test>` — корректно резолвит ts-jest и подхватывает `.env`.
**Подвох cooptypes:** когда `controller/node_modules` — симлинк на main, пакет внутри `node_modules/cooptypes -> ../../cooptypes` раскрывается **относительно main checkout**. `import { MarketContract } from 'cooptypes'` тянет d.ts из main, не из worktree. Если worktree обновлён, а main позади — TSC падает на отсутствующих типах. **Фикс:** перед TSC в worktree controller'а`git pull` в main checkout до того же коммита (или хотя бы где cooptypes/src синхронен) + `pnpm build` в `main/components/cooptypes/`.
## PR-flow
**Базовая ветка mono-ai-1 — `dev`.** Прямые коммиты в `dev` для мелких фиксов разрешены и не требуют feature-ветки/PR (отменено 2026-05-22 пользователем). Для крупных задач — feature-ветка (`feat/...` или `fix/...`) от dev и PR в dev; merge делает пользователь на GitHub. Push в `main` / `mvp` — по-прежнему только через PR.
**Не stash'ить `-u` при unstaged WIP пользователя.** Это создаёт окно для потери при drop/конфликте. Если нужно временно убрать unstaged — `git stash push -- <конкретные-paths>` либо коммит-в-feature, и только свои файлы. Кейс 2026-05-18: после `git stash -u`+`drop` при конфликте потерял WIP пользователя (infra.ts/config.ts/quasar.config.cjs и др.).
### Story-by-story для проекта «Стол заказов» (mono-ai-4 на marketplace2)
Каждая story из MVP-эпиков «Стол заказов» (`coopenomics/mono`, базовая ветка `marketplace2`, чекаут `~/mono-ai-4`, BMad-spec'и `_blago/.../components/3-minimalnyy-produkt/_bmad-output/`) идёт через PR.
Workflow:
1. Worktree от `marketplace2` на feature-ветке `feat/<E>-<S>-<slug>`.
2. Edits + unit-тесты; tsc + jest должны быть зелёные.
3. Commit + push feature-ветку.
4. `gh pr create --base marketplace2 --head feat/<E>-<S>-<slug>`.
5. Merge **пользователем на GitHub** (не вызывать `gh pr merge` без явной просьбы).
6. После merge — fetch + checkout marketplace2 в основной чекаут, удалить feature-ветку + worktree, запустить e2e / blockchain тесты против обновлённого marketplace2.
### Umbrella-PR на эпик vs цепочка PR
При работе story-by-story в одной feature-area **не плодить отдельные PR на каждую story с одинаковой целевой веткой**. Каждый последующий PR показывает кумулятивный diff (всё, что в head минус то, что уже мёрджнуто в base). Если предыдущие PR ещё не смерджены — в diff вылазят дубликаты файлов всех предыдущих stories.
**Default — umbrella-PR на эпик** (для крупных эпиков с >3 stories): одна `feat/<E>-epic` ветка + один PR; каждая story — отдельный коммит. Worktree последовательно, push после каждой story, PR обновляется. Так закрыт Эпик 1 Стола заказов (umbrella #380).
**Альтернатива — stacked-PRs с `base:<prev-feat>`:** каждый PR таргетится на предыдущую feature-ветку. После merge нижнего GitHub автоматически перетарджетит верхние. Требует дисциплины и тулинга.
**Анти-паттерн:** worktree от `feat/1-2-...`, потом от `feat/1-3-...`, и каждый PR в `marketplace2`. Цепочка branches правильная (изоляция), но цепочка PR — нет. Кейс Эпика 1 Стола заказов 2026-05-14: 11 PR `#370-#380` подряд от `marketplace2`, каждый +N stories назад. Пользователь дошёл до review #372 и обнаружил дубли. Закрыл #372-#379, оставил только #380.
## Локальные тесты
**Не запускать полный jest локально** ни в mono-ai-1, ни в mono-ai-4: живой dev-стек в docker (`nodeos`, `controller dev` nodemon, `parser dev`, `n8n`) вешает CPU/RAM и блокирует chain. Полный suite — задача CI после push'а PR.
В mono-ai-4 **запрещён параллельный режим jest** (worker-pool по умолчанию) — это вешает сервер. Если нужен unit-тест — точечный с `--runInBand`:
```bash
pnpm jest tests/unit/marketplace/marketplace-onboarding-service.test.ts --runInBand
```
`pnpm generate-schema` / `pnpm generate-client`**не запускать локально**; та же memory/CPU полка вешает контейнер controller'а. Либо CI, либо пользователь сам когда контейнер остановлен.
Перед коммитом достаточно `tsc --noEmit` (быстрый, не блокирует).
## SDK login canon
`@coopenomics/sdk` экспортирует `Client.create({api_url, chain_url, chain_id})` + метод `client.login(email, wif)`. Он сам:
1. Генерит `now` (ISO timestamp).
2. Подписывает приватным ключом (WIF) через eosjs.
3. Зовёт `Mutations.Auth.Login.mutation` с `{email, now, signature}`.
4. Возвращает `{tokens: {access: {token}, refresh: {token}}, account: {username}}`.
**Не дёргать `Mutations.Auth.Login` напрямую**`LoginInput` ждёт `{email, now, signature}`, генерация подписи внутри SDK Client. Refresh: `Mutations.Auth.Refresh.mutation` с `{access_token, refresh_token}`. Канон используется в `blago-cli/src/session/index.ts` (loginInteractive) и в EMP-коннекторе `connectors/cooperative-tsk-login-connector` (Story 11.5).
## Backend (controller) каноны
### 3 базовые роли — User / Member / Chairman
- **User** — обычный пайщик. Базовые потребительские права (заказывать, публиковать оферту, видеть свои данные).
- **Member** — **член совета** (не «член кооператива»!). User-права + read-only admin (видит склад, поток заказов, повестку — но не модерирует и не подписывает финальные действия).
- **Chairman** — председатель. User + admin (модерация, KU/whitelist/витрины, closing signature АПП-приёмки/выдачи, повестка совета на write).
Маппинг core-роли на extension-роль явно: User → orderer + опционально offerer/operator; Chairman → admin (полный write); Member → read-only admin (board_readonly). Пайщик может быть одновременно в нескольких extension-ролях — массив, не enum. Guard'ы в расширениях — локальные сейчас, в Phase 2 переключатся на платформенный CASL.
### `agreements` ссылается на существующий document registry_id
Когда расширение controller'а (marketplace, blagorost, любое следующее) хранит факт подписи документа пайщиком в глобальной on-chain таблице `agreements`, ссылка идёт через **существующий `registry_id` из платформенного реестра документов**, не через отдельный type-string типа `marketplace.cpp.stol-zakazov-v1`.
Поле `document_id` в `agreements` — FK на существующий platform registry. Extension-таблицы `*_onboarding_requirement``document_registry_id` ссылается на существующий ID. API запросов вида «какие документы подписаны member'ом» — `agreementsByMember(member_id, document_id_filter=[...])`.
**Технический долг платформы:** «Договор УХД сейчас не проходит через `agreements`» — отдельная задача core controller'а, вне scope конкретных расширений.
### Трёхуровневый онбординг расширений
Платформенный паттерн, обязателен для всех новых расширений controller'а.
**L1 — Кооператив (one-time):** председатель/совет принимает решение совета о подключении ЦПП, принимается положение ЦПП (статический документ из platform registry, через document factory с подстановкой параметров кооператива), оферта регистрируется в `coop_registration_offers_registry`.
**L2 — Пайщик при вступлении (per-membership):** в registration-flow появляется **выбор** ЦПП. Пайщик отмечает интересующие, document factory рендерит оферту с `{cooperative_params, member_params, agreement_date}`. Подпись пишется в глобальную on-chain `agreements`. Эта подпись **нивелирует** gate на столе расширения.
**L3 — Пайщик на рабочем столе (per-extension first visit):** backend проверяет через `agreementsByMember` — подписана ли оферта ЦПП. ДА → gate не показывается. НЕТ → gate показывается как explicit consent.
При проектировании любого нового расширения — обязательно три истории под три уровня. На MVP допустимо упростить: одинаковый `document_registry_id` для положения и оферты (физически разные документы могут быть в Phase 2).
### Marketplace asset через DI
В сервисах `components/controller/src/extensions/marketplace/**/*.service.ts` запрещён хардкод вида `const ASSET_DECIMALS = 4` / `const ASSET_SYMBOL = 'RUB'`. Decimals и symbol — через DI `MARKETPLACE_ASSET_CONFIG`:
```ts
@Inject(MARKETPLACE_ASSET_CONFIG) private readonly assetConfig: MarketplaceAssetConfig
// assetConfig.symbol, assetConfig.decimals
```
Канон-пример: `marketplace-order-create.service.ts`. См. `marketplace-asset.config.provider.ts` — мапит `config.blockchain.root_govern_symbol` / `root_govern_precision`. Разные среды (mainnet/testnet/dev) имеют разный symbol+precision.
### registry_id=800 (ReturnByAssetStatement) — клиринг, не членские взносы
Marketplace в монорепе живёт в **двух контурах**:
1. **Система клиринга** (старый, не используется) — registry_id=800. Не использовать в новых фичах.
2. **Система членских взносов** (текущий MVP) — документы лежат **рядом** с актами приёма-передачи и ТТН; другая группа registry_id.
Для нового документа Marketplace-членские-взносы: завести новый registry_id рядом с актами/ТТН и проложить цепочку `cooptypes → factory → controller → desktop`:
1. `@coopenomics/cooptypes`: новый тип документа + регистрация в registry.
2. `@coopenomics/factory`: generator (preview-структура + meta).
3. `@coopenomics/controller`: signed-document DTO + verify в сервисе.
4. `@coopenomics/desktop`: подпись через `Classes.Document` с новым registry_id.
## GraphQL каноны (controller + desktop)
### Описания @Field — бизнес-языком
В `@Field({ description })`, `@InputType`, `@ObjectType` нельзя писать «Story 4.1», «Эпик 3», «FR11a», «composite-entity», «dispatch pipeline», «tx_snapshot», «backend deterministic order_hash». Только пользовательский язык: «Идентификатор заказа», «ПВЗ получения», «Кол-во единиц товара». Story-ссылки и инвариант-комменты — только в inline-комментариях внутри сервиса.
### Enum вместо строковых литералов
Запрещены `if (offer.cycle_type === 'volume_based')`, `status: 'ACTIVE'`, `'PENDING_MODERATION'`. Любое поле с фиксированным набором (cycle_type, status, type, kind, role) — TypeScript `enum`, при необходимости `registerEnumType` для GraphQL. В тестах константы — тоже из enum, не дублирующие строки. Перед добавлением сравнения по строке — `enum MarketplaceOfferCycleType` / `MarketplaceOrderStatus` в `domain/entities/*.types.ts`.
### Пагинация — единый паттерн
В controller-resolver'ах пагинация делается единым каноническим паттерном:
- Вход: `@Args('options', { nullable: true }) options?: PaginationInputDTO` (импорт из `~/application/common/dto/pagination.dto.ts`, поля page/limit/sortBy/sortOrder).
- Выход: `createPaginationResult(ItemDTO, 'PaginatedXxx')` + сигнатура `Promise<PaginationResult<T>>` (items / totalCount / totalPages / currentPage).
- Repository принимает `PaginationInputDTO`, сам считает offset/limit/sort через TypeORM `findAndCount`.
Канон: `time-tracker.resolver.ts`, `expenses-management.resolver.ts`, `generation.resolver.ts`. Никаких локальных `{ limit, offset }`.
### Никаких raw GraphQL-строк в desktop
В `components/desktop/src/pages/**/api/index.ts` и аналогах запрещены конструкции:
```ts
const QUERY = `query Foo { ... }`;
await sendPOST('/v1/graphql', { query: QUERY, variables });
```
Даже с комментарием «техдолг до Zeus regen».
Обязательная процедура перед UI-кодом под новую GraphQL-операцию:
1. Добавить/изменить DTO/resolver в `components/controller/src/...` (code-first).
2. `pnpm run generate-schema` в `components/controller/` → пересоздать `controller/schema.gql`.
3. `pnpm run generate-client` в `components/controller/` → graphql-zeus кладёт клиент в `components/sdk/src/zeus/`.
4. `pnpm run build` в `components/sdk/` → unbuild собирает `dist/`.
5. В desktop импортировать `Mutations.<Domain>.<Name>` / `Queries.<Domain>.<Name>` из `@coopenomics/sdk` — типизировано end-to-end.
Если на шаге 1 не хватает поля — добавить и запустить весь цикл; не оставлять заглушку «пока».
### Строгая типизация desktop API из SDK через IInput['data']
Каждый вызов `client.Mutation` / `client.Query` в `components/desktop/src/**/api/index.ts`:
1. Принимает аргументом объект `data: IXxxInput`, где `IXxxInput = Mutations.<Domain>.<Action>.IInput['data']` (или `Queries...`) — тип берётся **прямо из @coopenomics/sdk**, не переописывается.
2. Передаёт в `variables` объект `data` целиком: `{ variables: { data } }`. Запрещено разворачивать поля: `{ variables: { data: { a, b, c } } }`.
Канон — `features/Branch/CreateBranch/{api,model}/index.ts`: тип в model `export type IXxxInput = Mutations.X.Y.IInput['data']`; функция в api `function (data: IXxxInput) { ... variables: { data } }`. Не делать `as` cast'ов.
## Frontend desktop — English имена
В `components/desktop/` и любом Vue/TS frontend коде **все имена идентификаторов — английские**:
- Имена Vue-компонентов: `BaseInput`, `BaseDialog`, `WalletCard`, `IdentityPanel`.
- Имена файлов и директорий: `shared/ui/BaseInput/BaseInput.vue`.
- CSS-классы: `.base-card`, `.wallet-card__icon`, `.id-panel__hero`.
- SCSS-переменные: `$primary`, `$prog-blagorost`, `$separator-color`.
- TS-типы, интерфейсы, переменные, функции: `interface WalletCardProps`, `function useWalletData()`.
**Why:** Unicode-имена ломают тулчейн (Vite/Webpack резолверы и aliases часто на ASCII-only regex; TypeScript symbol-resolution на не-ASCII нестабильно; ESLint `vue/component-name-in-template-casing` ждёт PascalCase ASCII; импорты `import БазоваяКнопка from '@/shared/ui/БазоваяКнопка'` невыносимы при review).
**Заголовки в .vue, label-ы кнопок, тексты в UI — по-русски** (это user-facing strings). Не путать с правилом «онтологические class_id по-русски» — то про EMP/ТЭМ и blago-документы, не про frontend.
**Кейс 2026-05-18:** при подготовке UX-спецификации для components/desktop ошибочно применил правило русских имён к Vue-компонентам (`БазоваяКнопка`, `БазовоеПолеВвода`); пользователь поправил.
## Стандарты процессов (.standard.yaml) — бизнес-языком
`components/contracts/cpp/**/*.standard.yaml` — документация для методолога/бухгалтера, не для разработчиков контракта. В `purpose`, `description`, `note`, `human` запрещены технические термины:
- никаких «callback», «soviet::exec», «soviet::createagenda», «AUTHORIZE_CALLBACK_SIGNATURE», «type-string», «registry N», «proposed расширение enum'а»;
- никаких «backend formирует», «controller вызывает», «contract отдаёт» — пишем кто что делает на уровне бизнеса (председатель / совет / заказчик / поставщик);
- технические `marketplace::propwroff`-имена в полях `action`/`name`/`triggered_by` оставляем как identifier'ы, но всё человеко-читаемое в `human`/`purpose`/`description` — на бизнес-словаре;
- бухгалтерские проводки `Дт 91 / Кт 10` — допустимы (бухгалтер их понимает);
- если процесс встроен в более общий — ссылаемся на стандарт по имени-человеку («типовой процесс решения совета»), не на техническую реализацию повестки.
Эталоны: `p.mkt.return.standard.yaml`, `p.cap.rid.standard.yaml`, `reg.coop.standard.yaml`. Антипример — `p.mkt.wroff.standard.yaml` в PR #399 review 2026-05-18 (был забит callback-описаниями и «type=mktwroff»).
## Vault & SERVER_SECRET
WIF админ-аккаунта (например `voskhod`) хранится в `vaults` PostgreSQL зашифрованным AES-256-CBC с ключом `sha256(SERVER_SECRET)`. Если `SERVER_SECRET` потом меняли — **старые записи разрушаются**, `decipher.final()` бросает `error:1C800064:Provider routines::bad decrypt`.
**Симптомы:**
- В логе coopback: `[VaultDomainService] Ошибка при получении WIF ключа для пользователя voskhod: bad decrypt`.
- В UI каскад `SignAgreementDialog` не закрывается; SPA отправляет `sendAgreement` корректно, но `wallet::signagree` on-chain не происходит.
- Следствие — `wallet::users[<coop>]` пуст, и любой последующий `is_can_transfer`/трансфер AXON падает на `Отправитель не является участником ЦПП кошелька`.
**Фикс:**
1. Достать живой WIF (для voskhod в dev — `5KQwrPbwdL6PhXujxW37FSSQZ1JiwsST4cqQzDeyXtP79zkvFD3` из boot config.ini, signature-provider).
2. Шифрануть им current SERVER_SECRET (см. `controller/src/utils/aes.ts` — sha256(SECRET) → AES-256-CBC, IV 16 байт, формат `ivHex:cipherHex`).
3. `UPDATE vaults SET wif='...', updated_at=now() WHERE username='voskhod' AND permission='active';`.
4. Перезапуск coopback **не нужен** — он читает каждый раз.
**Дефолт всех mono-репозиториев — `SECRET`.** Если в каком-то `.env` стоит другое — девиация, не норма. Перед re-encrypt'ом vault'а ВСЕГДА сначала смотреть `~/mono-ai-1/components/controller/.env` (или соседнего) — это origin truth для SERVER_SECRET.
**Кейс 2026-05-18 (Эпик 0):** в `mono-ai-5/components/controller/.env` стоял `e2e-fixture-secret-DO-NOT-USE-IN-PROD`, а WIF voskhod в vaults был зашифрован оригиналом — `SECRET`. Фикс — откатить SERVER_SECRET к `SECRET` и подровнять provider'а.
## Capital — фиксы билетов времени (PR #387 merged 2026-05-15)
В `components/controller/src/extensions/capital/` была серия багов в распределении билетов времени, закрытая PR #387 в dev. Три бага:
1. **`recalcDoneEstimatesForContributorProject` / `applyExplicitEstimateToTimeEntries`** раздавал «общий остаток пула» `(estimate total_committed) / N` всем creators, включая того, кто уже закоммитил. Фикс: личная доля `max(0, estimate/N own_committed_estimate)` через общий helper `redistributeIssueEstimateEntries`.
2. **`commitTime` partial split** создавал committed-запись без `entry_type` и `estimate_snapshot` — БД по default'у писала `entry_type='hourly'`, что ломало последующий recalc (фильтрует только `entry_type='estimate'`). Фикс: явно копировать оба поля.
3. **`declineCommit` / `handleDeclineCommit`** меняли только `commit.status='declined'`, но не возвращали `time-entries` в `is_committed=false`. Часы оставались в `total_committed_hours`. Фикс: `revertEntriesForDeclinedCommit` через новые `findCommittedByCommitHash` / `revertCommittedEntriesByCommitHash`.
**При симптомах** «25 ч подтверждено непонятно откуда» / «доступные часы не вернулись после decline» / «парные коммиты на одну работу» — первый чек: `grep -c redistributeIssueEstimateEntries time-tracking.interactor.ts` в контейнере > 5. Если нет — деплой устарел. Если есть, но баг — посмотреть `entry_type` у committed-записей по issue: legacy записи из БАГ #2 могут до сих пор быть с `entry_type='hourly'` для split-результатов от estimate (видны по `commit_hash IS NOT NULL AND entry_type='hourly' AND estimate_snapshot IS NULL` на DONE-задаче с estimate>0). Чинятся UPDATE'ом `entry_type → estimate` с правильным `estimate_snapshot`.
**Legacy data caveat:** `capital_time_entries` с `entry_type='hourly'` + `commit_hash != NULL` могут быть как (а) настоящей hourly работой до установки estimate, так и (б) split-наследием БАГ #2. Различить: если у задачи `estimate>0` и `DONE`, и записи hourly от тех же creators что в estimate-долях — это (б), чинить.
**Edge-case дробных остатков:** при `estimate=2.5` и одном creator, после commit'а 2 ч (`Math.floor < 1` для остатка) остаётся 0.5 ч uncommitted estimate, который никогда не закоммитится. Либо ручной DELETE uncommitted остатка, либо изменить estimate на целое (но estimate в `capital_issues` — on-chain, через UI mutation, не DELETE'ом в БД).
## Стол Заказов MVP — текущее состояние
Проект `1-prilozhenie-stol-zakazov` в blago (coopname voskhod, hash `feabc749…3841f73`). Кооперативная закупка/распределение имущества участка (продукты, товары, услуги); пилот — Красногорск; цель 6 мес: 10 кооперативов / 1200+ пайщиков.
**Локация:** `~/blago/production/1-prilozhenie-stol-zakazov/`.
**Структура артефактов:**
- `_bmad-output/planning-artifacts/` (project-уровень): `prd.md`, `prd-validation-report.md`, `ux-design-specification.md`, `architecture.md` (status:complete 2026-05-12).
- **`components/3-minimalnyy-produkt/_bmad-output/planning-artifacts/epics.md`** (SoT для MVP) — `stepsCompleted=[1,2,3,4]`, `status: complete 2026-05-12`, 65 FRs → 11 эпиков → 57 stories. **НЕ создавать дубль на верхнем уровне `_bmad-output/planning-artifacts/`** — MVP-компонент имеет собственный bmad-output.
- `requirements/` (5 файлов): `04-brif`, `0b-protsessy`, `0f-prd`, `7e-uxui`, `d6-arkhitektura` — дубли _bmad-output (намеренно, см. правило о дублях BMad-артефактов в global memory).
**Locked Decisions L1L9:**
- **L1:** порядок подписей АПП (приёмка поставщик→председатель финально / выдача председатель→заказчик финально).
- **L2:** `o.mkt.payout` baseline `Дт 86 / Кт 51` без счёта 60.
- **L3:** реверты исключены — compensating forward с собственным `operation_id`.
- **L4:** геокарта КУ обязательна на трёх столах; lat/lng в `PlaceDomainEntity`.
- **L5 / L9:** «Системный конструктор ЦПП» → реализован как трёхуровневый онбординг расширений (см. выше).
- **L6:** без отрицательного баланса в MVP (отменяет NFR-R5 PRD).
- **L7:** enum 10 кооп-категорий (овощи/фрукты, молочные, мясо, рыба, хлеб, бакалея, напитки, готовая еда, услуги, прочие).
- **L8:** двухслойная схема подписания — глобальная on-chain `agreements` (SoT) + локальные `*_onboarding_requirement`/`*_onboarding_state` per-extension.
- **L10/L11/L13:** consolidated request backend-only / cycle_type backend variation / pull-модель отчётности.
**Прогресс по эпикам (на 2026-05-15):**
- **Эпик 1** — MERGED в `marketplace2`: PR #368/#370/#371/umbrella #380.
- **Эпик 2 «Сеть ПВЗ»** — MERGED PR #381 (после rebase). Workspace `market-pvz`, KU details + Yandex geocoder, Zeus SDK.
- **Эпик 11 Story 11.1 (Ledger2 canonical actions)** — MERGED PR #375 на C++ стороне. **TS-сторона cooptypes НЕ закрыта**: `cooptypes/src/contracts/marketplace/actions/index.ts` экспортирует только LEGACY клиринговые actions, `interfaces/marketplace.ts` auto-generated из устаревшего ABI. **Блокер Эпика 4** — нужен отдельный pre-эпик PR `feat/S11-1-cooptypes-canonical`: ABI regen через `eosio-abi2ts` из новой `marketplace.abi.json` после `coopcontracts` build, либо ручное добавление 18 canonical actions + canonical tables + canonical interfaces.
- **Эпик 3 «Витрина»** — IN REVIEW. PR #382 (`feat/E3-vitrina`) OPEN MERGEABLE. 6 коммитов (Stories 3.13.5 + BC-sync seam), 67 unit-тестов. Stories 3.4 (CAS counters) — callback-target для Эпика 4 + scaffolding `marketplace-order-sync.service.ts` (skeleton, throw NOT_IMPLEMENTED).
- **Эпики 4-10** — BACKLOG. Issues 598-7 … 598-13 разложены; story-requirements в `598-N-…-requirements/`.
**Открытые фоллоуапы Эпика 1:**
- L3 mutation `marketplaceSignOnboardingOffer` (write-mutation pool + `sndagreement`).
- Source-маркер `'registration_flow'` vs `'extension_gate'` в DTO.
- `marketplaceAcceptCpp` валидация повестки совета — после Эпика 8 (FR40).
- Финальный юридический текст оферты — `todo-tspp-templates.md` (блокирует Stories 1.7/1.9/1.11 в продовой подаче).
- Story 1.5 интеграционный тест против тестовой ноды ЦК — после Эпика 11.
**Реальное состояние brownfield (на marketplace2 @ d98041d):**
| Слой | Готово (membership) | Donor-клиринг (нужно решить судьбу) |
|---|---|---|
| ledger2 C++/TS реестры | 12 операций `o.mkt.*`, счета 10/91, кошельки `w.mkt.member`/`w.mkt.payout`/`w.wal.member`, WalletOp `REVOKE` | — (legacy `o.mkt.supply/recv` удалены) |
| YAML-стандарты `p.mkt.{supply,return,wroff}` | canonical имена actions | — |
| C++ actions (`marketplace.hpp` + 30 .cpp) | **ничего** из canonical | `orderoffer/accept/authcontrib/authreturn/supply/...` ~1660 LOC; legacy Wallet, не ledger2 |
| process-registry в controller | заглушки под membership (`p.mkt.reqst` убран) | — |
| cooptypes/contracts/marketplace TS-actions | нет canonical | 24 клиринговых обёртки |
| controller/application + domain/marketplace | нет canonical | 23 DTO + interactor + resolver + 6 interfaces |
| controller/extensions/marketplace | — | для категорий Ozon (clean arch, 7 TypeORM entities); может пригодиться для каталога Offer'ов |
| controller/extensions/marketplace-cards | — | минимальный каркас карточек |
| desktop/pages/Marketplace | нет canonical | 11 страниц под клиринг; `desktop/extensions/market` пуст |
**Решение 2026-05-12:** стратегии миграции не делаем — donor уже не работает по старой модели; собираем новую membership-модель в существующем контуре, donor-код переписывается / удаляется напрямую без переходников.
В `/bmad-create-architecture` MVP **не вводить adapter-слой и не описывать миграционные пути**. Прямо фиксировать: какие C++ actions/DTO/Vue-страницы из donor-листа удаляются, какие переписываются под canonical (`signsupp/signchair/signiss1/signiss2/acceptbatch/declinebatch/expirecycle/prepship/createorder(новая сигнатура)/cancelorder`), какие сохраняются (shipment/coopstock — если попадают в MVP scope, отдельно проверить).
**Обязательная enforcement-база для backend**`mono-ai-4/components/controller/CLAUDE.md` (Composite-Entity `db/bc/derived`, Write-mutation pool с placeholder/sync_key dedup, ParserClient + Redis Streams, ForkRegistry, ADR-002/008/009/011/012; параметры через `config/blockchain.config.ts`, не magic numbers).
+39
View File
@@ -0,0 +1,39 @@
k# Conventional Commits
### Основные типы коммитов:
- **`feat`**: Добавление новой функциональности (feature).
- Пример: `feat: добавлена возможность загрузки файлов`
- **`fix`**: Исправление бага.
- Пример: `fix: исправлена ошибка отображения кнопки на мобильных устройствах`
- **`chore`**: Изменения, не влияющие на исходный код (например, обновление зависимостей или инструментария).
- Пример: `chore: обновление зависимостей`
- **`docs`**: Изменения в документации.
- Пример: `docs: обновлено руководство пользователя`
- **`style`**: Изменения стиля кода, не влияющие на его функциональность (форматирование, пробелы, и т.д.).
- Пример: `style: исправлены отступы в коде`
- **`refactor`**: Изменения в коде, которые не исправляют баги и не добавляют новую функциональность.
- Пример: `refactor: улучшена структура класса`
- **`perf`**: Изменения, направленные на улучшение производительности.
- Пример: `perf: оптимизирована работа с массивами`
- **`test`**: Добавление или изменение тестов.
- Пример: `test: добавлен тест для проверки функции отправки сообщений`
### Дополнительные типы коммитов:
- **`build`**: Изменения, связанные с процессом сборки или зависимостями.
- Пример: `build: обновление конфигурации Webpack`
- **`ci`**: Изменения, касающиеся настроек непрерывной интеграции (например, Travis, Jenkins).
- Пример: `ci: настройка Travis для автоматических сборок`
- **`revert`**: Откат на предыдущие изменения.
- Пример: `revert: откат коммита e0b5107`
+139
View File
@@ -0,0 +1,139 @@
# Запуск mono dev-стека на macOS
Полная пошаговая инструкция, как поднять backend (`coopback`) + parser (`cooparser`) + блокчейн-ноду + БД на macOS через Docker Desktop. Прошёл — отметь, ниже разобраны типичные грабли.
## TL;DR
```bash
cd ~/dacom-code/foundation/monocoop
docker compose up -d # 1. поднять базу
./scripts/dev-setup-macos.sh # 2. одной командой (см. ниже скрипт)
```
Если скрипта ещё нет — выполняй шаги ниже руками.
## Шаги
### 1. Поднять контейнеры
```bash
docker compose up -d
```
Поднимутся: `node` (NodeOS), `mongo`, `monoredis`, `postgres`, `coopback`, `cooparser`. **MinIO** входит в дефолт. **OpenSearch** — нет (тяжёлый, см. опц. сервисы).
### 2. Проверить чтоб .env'ы указывали на service-имена, а не localhost
`components/controller/.env`:
- `MONGODB_URL=mongodb://mongo:27017/cooperative-x`
- `REDIS_HOST=monoredis`
- `POSTGRES_HOST=postgres`, `POSTGRES_PASSWORD=postgres!23!23`
- `BLOCKCHAIN_RPC=http://node:8888`
- `SIMPLE_EXPLORER_API=http://cooparser:4000`
- `MINIO_ENDPOINT=minio:9000`
- `CHAIN_ID=<реальный chain_id, см. ниже>`
`components/parser/.env`:
- `MONGO_EXPLORER_URI=mongodb://mongo:27017/cooperative-x`
- `REDIS_HOST=monoredis`
- `API=http://node:8888`
- `SHIP=ws://node:8080`
**Почему service-имена:** все контейнеры в bridge-сети `monocoop_default`. Внутри контейнера `127.0.0.1` = сам контейнер, не host. На macOS `network_mode: host` в Docker Desktop работает плохо — используем bridge + service names.
### 3. Узнать живой chain_id
```bash
curl -s http://localhost:8888/v1/chain/get_info | jq -r .chain_id
```
И вписать в `components/controller/.env``CHAIN_ID=...`. **Если chain_id в .env не совпадает с живым — on-chain транзакции упадут на verify, хотя приложение запустится.**
### 4. Если правил .env — пересоздать контейнер (не restart!)
```bash
docker compose up -d --force-recreate --no-deps coopback cooparser
```
`docker restart` **не перечитывает** `env_file`. `--no-deps` — чтобы не пересоздавать БД (потеряются данные).
### 5. Native binding libxmljs2 — пересборка под Linux
На свежем чекауте `pnpm install` запускается на macOS, и `libxmljs2` собирает Mach-O бинарник. В Linux-контейнере он падает:
```
Error: .../xmljs.node: invalid ELF header ERR_DLOPEN_FAILED
```
**Фикс** (один раз после `pnpm install`):
```bash
docker exec monocoop-coopback-1 sh -c '
cd /app/node_modules/.pnpm/libxmljs2@0.37.0/node_modules/libxmljs2 \
&& rm -rf build \
&& PATH="$PWD/node_modules/.bin:$PATH" npm run install
'
docker restart monocoop-coopback-1
```
Проверка — magic bytes Linux ELF:
```bash
docker exec monocoop-coopback-1 sh -c \
'head -c 4 /app/node_modules/.pnpm/libxmljs2@0.37.0/node_modules/libxmljs2/build/Release/xmljs.node | od -c -N 4'
# Должно быть: 177 E L F
# Если cf fa ed fe — это macOS Mach-O, фикс не применился.
```
### 6. Дождаться cold-start coopback (~56 минут)
`ts-node` без cache + DI tree NestJS = долго. Первые логи появляются спустя ~5 минут после старта контейнера.
```bash
docker logs -f monocoop-coopback-1 | grep -E 'NestJS app|Nest application|Error'
```
Готово, когда видишь:
```
Nest application successfully started
NestJS app with Express routes running on port 2998
```
Проверка:
```bash
curl -s -X POST -H 'Content-Type: application/json' \
-d '{"query":"{__typename}"}' http://localhost:2998/v1/graphql
# {"data":{"__typename":"Query"}}
```
## Опциональные сервисы
### OpenSearch (поиск)
```bash
docker compose --profile search up -d opensearch
```
Затем в `components/controller/.env`:
```
OPENSEARCH_ENABLED=true
```
И пересоздать coopback:
```bash
docker compose up -d --force-recreate --no-deps coopback
```
## Грабли (если опять провозился пол-дня)
| Симптом | Причина | Фикс |
|---|---|---|
| `invalid ELF header` | host'овый `pnpm install` положил Mach-O | См. п. 5 — пересборка libxmljs2 в контейнере |
| `MongooseServerSelectionError: ECONNREFUSED 127.0.0.1:27017` | .env на localhost вместо service-имени | См. п. 2 |
| `password authentication failed for user "postgres"` | в .env `POSTGRES_PASSWORD=postgres` вместо `postgres!23!23` | См. п. 2 |
| Coopback ушёл в restart-loop, но рядом есть другой `monocoop-coopback-1` Up | Случайно запустился старый `components/controller/docker-compose.yml` (network_mode: host, без bind-mount, без CMD) | `docker stop coopback && docker rm coopback` |
| `docker restart` не подхватил новые переменные .env | `restart` не перечитывает `env_file` | `docker compose up -d --force-recreate --no-deps <svc>` |
| Coopback зависает на 5+ минут, лога нет | Это нормально для cold-start ts-node | Подождать. CPU должен крутиться ≥50%. Если CPU = 0% — другая проблема |
| `[VaultDomainService] Ошибка при получении WIF... bad decrypt` | SERVER_SECRET не совпадает с тем, чем шифровали WIF в БД | См. CLAUDE.md → раздел Vault & SERVER_SECRET. Дефолт — `SECRET` |
| Транзакции падают на on-chain verify | CHAIN_ID в .env не совпадает с живым | См. п. 3 |
| `Custom endpoint \`minio://9000\` was not a valid URI` на bootstrap | `MINIO_ENDPOINT` без схемы | `MINIO_ENDPOINT=http://minio:9000` (со схемой!) |
| nodeos в restart-loop с `Database dirty flag set` после sleep/crash Docker Desktop | unclean shutdown chain state | `docker stop monocoop-node-1`; `mv blockchain-data/state-history{,.broken-$(date +%s)}`; `docker compose up -d node` — nodeos сам сделает replay |
| Cold-start coopback 10+ минут (вместо обычных 3-5) | ts-node без cache + bind-mount через osxfs + параллельная нагрузка (nodeos replay) | Подождать; в будущем — `tsx` / `ts-node --swc` для dev-режима |
+118
View File
@@ -0,0 +1,118 @@
# Multi-stage build для `dicoop/mono-base`.
#
# Стадии:
# 1. builder — full toolchain: pnpm + lerna + apt dev-headers (gcc,
# libcairo2-dev, ...) + WeasyPrint в venv. Здесь делаются
# `pnpm install` (с devDeps), `lerna run build`, потом
# `pnpm prune --prod` (devDeps выкидываются из workspace
# node_modules — экономит ~1.5GB).
# 2. runtime — slim образ без dev-headers и без gcc. Только runtime
# libs WeasyPrint + готовый /app + venv. Глобальные pnpm/lerna
# ставятся отдельно для удобного запуска `pnpm -F <pkg> run start`.
#
# Финальный размер: ~1-1.5GB (вместо 7.36GB в одностадийной сборке).
# Все потребители mono-base (controller/desktop/parser/notifications/
# notificator/boot) пользуются одним и тем же тонким runtime-образом
# через `FROM dicoop/mono-base:<tag>` + `CMD`.
# ── Stage 1: builder ──────────────────────────────────────────────────
FROM node:22-slim AS builder
WORKDIR /app
# Build-time системные deps. Тяжёлые `-dev`-пакеты (для компиляции
# native-bindings + WeasyPrint native deps) сюда, в runtime их не
# тащим. `--no-install-recommends` экономит ещё ~150MB.
RUN apt-get update && apt-get install -y --no-install-recommends \
python3 python3-pip python3-venv \
build-essential gcc g++ python3-dev \
libcairo2-dev libffi-dev libjpeg-dev libopenjp2-7-dev zlib1g-dev \
libpango-1.0-0 libpangoft2-1.0-0 libpangocairo-1.0-0 libcairo2 \
shared-mime-info \
&& rm -rf /var/lib/apt/lists/*
# WeasyPrint в venv — переедет в runtime-stage целиком через COPY.
RUN python3 -m venv /venv \
&& /venv/bin/pip install --no-cache-dir WeasyPrint==67
# pnpm пинится через `packageManager` поле в корневом package.json
# (corepack-стандарт). Без пина CI каждый раз тянет latest, а pnpm 10
# ужесточил политику build-скриптов и валит `--frozen-lockfile` с
# ERR_PNPM_IGNORED_BUILDS на native-пакетах (electron / esbuild / …).
RUN corepack enable && npm install -g lerna --no-fund --no-audit
# Сначала манифесты (для кэш-friendly install). `.dockerignore` уже
# выкидывает node_modules/dist/.git, поэтому `COPY .` лёгкий.
COPY . .
# Используем существующий lockfile. Если он не совпадает с workspace —
# падать сразу, не дрейфовать незаметно.
RUN pnpm install --frozen-lockfile
# Сборка всех пакетов через lerna-граф (зависимости собираются в
# правильном порядке). Никаких --filter — пусть собирается всё, чтобы
# образ годился любому потребителю mono-base.
RUN lerna run build
# Удалить devDeps из всех workspace node_modules. Это и есть основная
# оптимизация размера — typescript, vitest, eslint, unbuild, ts-node-cli,
# desktop-сборщики и пр. удаляются из финального дерева.
#
# - `CI=true` отключает интерактивный prompt («вы уверены что снести
# modules?») — без TTY pnpm иначе абортится с
# ERR_PNPM_ABORTED_REMOVE_MODULES_DIR_NO_TTY.
# - `--ignore-scripts` подавляет lifecycle hooks (prepare/postinstall)
# после prune. Иначе pnpm дёргает `quasar prepare` в desktop'е,
# а quasar (devDep) уже снесён → ELIFECYCLE.
#
# Все production-сервисы переведены на runtime без devDeps:
# cooparser → `node ./dist/index.cjs`
# notifications → `node ./dist/sync/sync-runner.cjs` (entry добавлен в unbuild)
# coopback → `ts-node` + `tsconfig-paths` (оба в deps)
# desktop → `node dist/ssr/index.js`
# boot:remote → `node /app/components/boot/dist/index.cjs boot:remote`
RUN CI=true pnpm prune --prod --ignore-scripts
# ── Stage 2: runtime ──────────────────────────────────────────────────
FROM node:22-slim AS runtime
WORKDIR /app
# Только runtime-библиотеки WeasyPrint (без `-dev` headers и без gcc).
# `python3` нужен потому что venv в /venv/bin/python — символическая
# ссылка на системный интерпретатор; без него `weasyprint` падает с
# `python: not found`. `procps`/`wget` — для дебага/healthcheck'ов
# из docker-compose.
#
# `ca-certificates` обязателен: node:22-slim его не содержит, а
# native-биндинги типа @livekit/rtc-node (Rust + rustls + rustls-native-certs)
# читают корни ТОЛЬКО из системного store. Без файла
# /etc/ssl/certs/ca-certificates.crt любой TLS handshake из такого
# биндинга падает с "invalid peer certificate: UnknownIssuer" —
# даже для валидной LE-цепочки (Node-стек при этом работает,
# у него свои вшитые корни). Инцидент 2026-05-21: secretary в
# coopback не мог подключиться к wss://chatcooprtc.coopenomics.world.
RUN apt-get update && apt-get install -y --no-install-recommends \
ca-certificates \
python3 \
libpango-1.0-0 libpangoft2-1.0-0 libpangocairo-1.0-0 libcairo2 \
libffi8 libjpeg62-turbo libopenjp2-7 zlib1g shared-mime-info \
procps wget \
&& rm -rf /var/lib/apt/lists/* \
&& update-ca-certificates
# Python venv с WeasyPrint, готовый к использованию.
COPY --from=builder /venv /venv
ENV PATH="/venv/bin:$PATH"
# Приложение целиком (с уже урезанными до prod node_modules).
COPY --from=builder /app /app
# Глобальные pnpm/lerna — нужны чтобы потребители mono-base могли
# делать `CMD ["pnpm","-F","<pkg>","run","start"]` в production.
# pnpm активируется через corepack (версия из `packageManager` корневого
# package.json — синхронно со builder-стадией).
RUN corepack enable && npm install -g lerna --no-fund --no-audit
# Sanity-check: WeasyPrint работает и виден через PATH.
RUN weasyprint --version
+120
View File
@@ -0,0 +1,120 @@
# Цифровой Кооператив
<!-- badges -->
![License](https://img.shields.io/badge/license-BY--NC--SA%204.0-blue)
![Node](https://img.shields.io/badge/node-%3E%3D20-green)
![pnpm](https://img.shields.io/badge/pnpm-9-orange)
Платформа «Цифровой Кооператив» — комплексное программное обеспечение для управления кооперативными организациями на основе блокчейна EOSIO. Система обеспечивает полный цикл управления кооперативом: от регистрации пайщиков и электронного документооборота до проведения собраний и финансового учёта. Построена на принципах прозрачности, децентрализации и простой электронной подписи.
Проект является частью экосистемы [Кооперативная Экономика](https://coopenomics.world).
## Архитектура
| Компонент | Пакет | Описание |
|-----------|-------|----------|
| [boot](components/boot) | `@coopenomics/boot` | CLI для инициализации и управления блокчейн-инфраструктурой |
| [cleos](components/cleos) | `@coopenomics/cleos` | Утилита командной строки для работы с блокчейн-кошельком |
| [contracts](components/contracts) | `@coopenomics/contracts` | Смарт-контракты EOSIO на C++ |
| [controller](components/controller) | `@coopenomics/controller` | GraphQL API сервер (NestJS) |
| [cooptypes](components/cooptypes) | `cooptypes` | Общие типы и интерфейсы блокчейн-контрактов |
| [desktop](components/desktop) | `@coopenomics/desktop` | Рабочий стол кооператива (Vue 3 + Quasar) |
| [factory](components/factory) | `@coopenomics/factory` | Генератор юридических документов |
| [migrator](components/migrator) | `migrator` | Утилита миграции данных |
| [notifications](components/notifications) | `@coopenomics/notifications` | Библиотека уведомлений на основе Novu |
| [parser](components/parser) | `@coopenomics/parser` | Индексатор блокчейна через State History Plugin |
| [sdk](components/sdk) | `@coopenomics/sdk` | TypeScript SDK для GraphQL API |
| [setup](components/setup) | `@coopenomics/setup` | Мастер первоначальной настройки |
## Быстрый старт
### Предварительные требования
- Node.js >= 20
- pnpm 9
- Docker и Docker Compose
- [WeasyPrint](https://doc.courtbouillon.org/weasyprint/stable/first_steps.html#installation) (для генерации PDF)
### Установка
```bash
pnpm install
```
### Конфигурация
```bash
pnpm run setup
```
Интерактивный мастер создаст необходимые `.env` файлы для всех компонентов.
### Запуск инфраструктуры
```bash
docker compose up -d
pnpm run reboot
```
## Разработка
### Бэкенд (controller + parser)
```bash
pnpm run dev:backend
```
### Фронтенд (desktop)
```bash
pnpm run dev:desktop
```
### Библиотеки (factory + cooptypes)
```bash
pnpm run dev:lib
```
### Все сервисы одновременно
```bash
pnpm run dev:all
```
> **Примечание:** установка пакетов производится только через фильтр: `pnpm add <пакет> --filter <компонент>`
## Тестирование
```bash
# Все тесты
pnpm run test
# Юнит-тесты (cooptypes, parser, notifications)
pnpm run test:unit
# Компонентные тесты (factory)
pnpm run test:component
# Интеграционные тесты (boot + blockchain)
pnpm run test:integration
```
## Сборка
```bash
# Библиотеки (cooptypes, factory)
pnpm run build:lib
# Смарт-контракты
pnpm run build:contracts:all
# Desktop (SSR)
pnpm --filter @coopenomics/desktop run build
```
## Лицензия
Продукт Потребительского Кооператива «ВОСХОД» распространяется по лицензии [BY-NC-SA 4.0](https://creativecommons.org/licenses/by-nc-sa/4.0/legalcode.ru).
Разрешено делиться, копировать и распространять материал, адаптировать и создавать производные произведения при условии указания авторства и сохранения той же лицензии. Коммерческое использование запрещено.
+129
View File
@@ -0,0 +1,129 @@
# 📋 Резюме создания компонентов Notifications
## ✅ Что создано
### 1. 📚 Библиотека `@monocoop/notifications`
**Расположение:** `components/notifications/`
**Функции:**
- ✅ Типизированные интерфейсы для workflow с Zod
- ✅ Builder паттерн для создания workflow
- ✅ Базовые шаблоны для email, in-app, push, SMS
- ✅ Автоматическая конвертация Zod схем в JSON Schema для Novu
- ✅ Экспорт всех workflow для использования в других пакетах
**Структура:**
```
src/
├── types/ # Базовые типы и интерфейсы
├── base/ # Утилиты и настройки по умолчанию
├── workflows/ # Папки с workflow
│ └── welcome/ # Пример приветственного workflow
└── index.ts # Главный экспорт
```
### 2. 🚀 NestJS приложение `@monocoop/notificator2`
**Расположение:** `components/notificator2/`
**Функции:**
- ✅ Автоматический upsert всех workflow в Novu при запуске
- ✅ RESTful API для триггера уведомлений
- ✅ Типизированная валидация payload
- ✅ Health check endpoints
- ✅ Использует библиотеку notifications для типов
**API Endpoints:**
- `GET /api/notifications/health` - Health check
- `GET /api/notifications/workflows` - Список workflow
- `POST /api/notifications/trigger` - Универсальный триггер
- `POST /api/notifications/trigger/welcome` - Триггер welcome workflow
- `POST /api/notifications/workflows/upsert-all` - Принудительный upsert
## 🔧 Как использовать
### 1. Настройка библиотеки notifications
```bash
cd components/notifications
pnpm install # или npm install
pnpm build # для компиляции TypeScript
```
### 2. Настройка notificator2
```bash
cd components/notificator2
pnpm install # или npm install
# Настройка окружения
cp .env.example .env
# Добавить NOVU_API_KEY в .env
# Запуск
pnpm start:dev
```
### 3. Добавление нового workflow
**В библиотеке notifications:**
```typescript
// components/notifications/src/workflows/order/order-workflow.ts
export const orderWorkflow = WorkflowBuilder
.create<OrderPayload>()
.name('Order Confirmation')
.workflowId('order-confirmation')
.payloadSchema(orderPayloadSchema)
.addSteps([...])
.build();
```
**Регистрация в index.ts:**
```typescript
// components/notifications/src/workflows/index.ts
import { orderWorkflow } from './order';
export const allWorkflows = [
welcomeWorkflow,
orderWorkflow, // ← добавить новый workflow
];
```
### 4. Использование API
**Триггер welcome workflow:**
```bash
curl -X POST http://localhost:3000/api/notifications/trigger/welcome \
-H "Content-Type: application/json" \
-d '{
"subscriberId": "user-123",
"email": "user@example.com",
"payload": {
"userName": "Иван Иванов",
"userEmail": "user@example.com",
"age": 25
}
}'
```
## 🎯 Преимущества архитектуры
1. **Типобезопасность** - Zod схемы обеспечивают валидацию на уровне TypeScript и runtime
2. **Разделение ответственности** - Библиотека содержит только типы, сервер - логику
3. **Расширяемость** - Легко добавлять новые workflow
4. **Автоматизация** - Workflow автоматически синхронизируются с Novu
5. **Переиспользование** - Типы можно использовать в других частях системы
## 🔄 Workflow при запуске
1. **Запуск notificator2**
2. **Чтение всех workflow из библиотеки**
3. **Проверка существования в Novu**
4. **Создание/обновление workflow**
5. **Готов к приёму запросов на триггеры**
## 📁 Структура как в testFramework2.ts
Вся логика из `testFramework2.ts` была перенесена в structured архитектуру:
-`buildWorkflowData``WorkflowBuilder`
-`baseSteps``createEmailStep`, `createInAppStep`, etc.
-`upsertWorkflow``NovuService.upsertWorkflow`
-`triggerWorkflow``NovuService.triggerWorkflow`
- ✅ Типизация payload → Zod схемы + TypeScript типы
+55
View File
@@ -0,0 +1,55 @@
# TASKS.md — Прогресс выполнения задач
## Завершённые задачи
### 1-6. Предыдущие задачи (см. git history)
- ✅ Dev-окружение, Security, Тесты, README, AGENTS.md, Setup
- ✅ Поисковая система документов (OpenSearch)
- ✅ Процессы (Capital extension)
---
## Текущая задача: Генерация отчётов ФНС (расширение reports)
### Документы ФНС для генерации:
1. **6-НДФЛ** — ежеквартально (XSD: NO_NDFL6.2)
2. **4-ФСС (ЕФС-1)** — ежеквартально
3. **РСВ** — ежеквартально (XSD: NO_RASCHSV)
4. **ПСВ** — ежемесячно (XSD: NO_PERSSVFL)
5. **Бухгалтерский баланс** — ежегодно (XSD: NO_BUHOTCH) — КЛЮЧЕВОЙ
6. **ДУСН** — декларация УСН ежегодно (XSD: NO_USN)
7. **Уведомление о страховых взносах** — ежемесячно с 2026 (XSD: UT_UVISCHSUMNAL)
8. **УУСН** — уведомление УСН
### 10. Генерация отчётов ФНС (доработка) ✅
- [x] Фабрика генераторов (ReportRegistryService)
- [x] 8 генераторов (Бухбаланс, 6-НДФЛ, РСВ, ПСВ, ДУСН, 4-ФСС, Увед. взносы, УУСН)
- [x] GraphQL API (getAvailableReports, generateReport)
- [x] Генераторы переписаны по XSD — структура соответствует схемам ФНС
- [x] 48 unit-тестов для всех генераторов
- [x] Desktop UI (страница отчётов) — расширение reports
- [x] Интеграция с реальными данными ledger через LedgerInteractor
- [x] OrganizationDataInput DTO для передачи данных организации
### Архитектура:
- Расширение `reports` в `components/controller/src/extensions/`
- Фабрика XML отчётов: на вход данные за период → на выходе XML
- Валидация по XSD схемам
- Desktop UI: магазин приложений → установка → рабочий стол отчётов
### Подзадачи:
- [x] **8.1 Исследование**: Все XSD разобраны, format.nalog.ru изучен
- [x] **8.2 Инфраструктура**: Расширение reports, ReportRegistryService (фабрика)
- [x] **8.3 XML генератор**: Фабричный подход — IReportGenerator interface
- [x] **8.4 Бухбаланс**: BuhotchGenerator — счета 51, 80, 86 из ledger
- [x] **8.5 6-НДФЛ**: Ndfl6Generator — нулевая
- [x] **8.6 4-ФСС**: Zero generator — нулевая
- [x] **8.7 РСВ**: Zero generator — нулевая
- [x] **8.8 ПСВ**: Zero generator — нулевая
- [x] **8.9 ДУСН**: Zero generator — нулевая
- [x] **8.10 Уведомление о взносах**: Zero generator — нулевая
- [x] **8.11 УУСН**: Zero generator — нулевая
- [x] **8.12 GraphQL API**: getAvailableReports + generateReport
- [ ] **8.13 XSD валидация + тесты**: Проверка по схемам
- [ ] **8.14 Desktop UI**: Страница отчётов в магазине приложений
- [ ] **8.15 Ledger интеграция**: Реальные данные из ledger_operations
+64
View File
@@ -0,0 +1,64 @@
# Test Plan — pnpm run test
## Архитектура
```
pnpm run test
├── cooptypes — vitest run (smoke tests exports) ✅ 4/4
├── parser — vitest run (config smoke tests) ✅ 3/3
├── factory — vitest run (document generation tests) 🔧 17/85 → need mocks
├── sdk — vitest run (API integration tests) 🔧 TODO
├── notifications — vitest run (workflow tests) 🔧 TODO
├── controller — jest / vitest (NestJS unit tests) 🔧 TODO
└── boot — vitest run (blockchain integration) 🔧 53/60
```
## Статус по компонентам
### cooptypes ✅ DONE
- 4 smoke-теста экспортов
- Не требует инфраструктуры
### parser ✅ DONE
- 3 smoke-теста конфигурации
- Не требует инфраструктуры
### factory 🔧 IN PROGRESS
- **Проблема**: тесты обращаются к parser API (`SIMPLE_EXPLORER_API`) для get-tables/get-actions
- **Решение**: Уже есть мок-система в `src/Utils/testMocks.ts` + `matchMock.ts`
- **Нужно**: Добавить моки для ВСЕХ документов:
- [ ] cooperative data mock (registrator.coops table)
- [ ] soviet boards mock — уже есть через test setup в MongoDB
- [ ] draft templates mock (draft.drafts + draft.translations tables)
- [ ] decision data mocks (soviet.decisions table)
- [ ] Мок для ReturnByMoney документов
- [ ] Все документы 1000+ серии
- **Текущие рабочие моки**: meet tables, votefor actions, returnByMoneyDecision actions
- **После мокирования**: все 85 тестов должны проходить
### boot 🔧 NEEDS REBOOT
- capital.test — 53/60 тестов проходят (после чистого reboot)
- wallet.test — нужен полный boot с agreements
- registrator.test — нужен полный boot
- capital-import.test — отдельный тест импорта
- **Требует**: pnpm run reboot перед запуском
### sdk 🔧 TODO
- 1 тест файл с login + fetch extensions
- Требует запущенный controller
- Нужно: обновить chain_id, api_url, credentials
### controller 🔧 TODO
- Все старые тесты удалены (устаревшие)
- NestJS-приложение — нужны тесты через @nestjs/testing
- Минимум: unit-тесты domain-логики, smoke-тест GraphQL API
### notifications 🔧 TODO
- Нет тестов
- Нужно: smoke-тесты workflow builder
### desktop — SKIP (нет тестов, UI-тестирование)
## Root script требования
- `pnpm run test` — запускает ВСЕ тесты
- fail-fast: если один пакет падает — весь pipeline падает
- Последовательный запуск (не параллельный)
Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.8 KiB

File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
-18
View File
@@ -1,18 +0,0 @@
/*!
* Lunr languages, `Danish` language
* https://github.com/MihaiValentin/lunr-languages
*
* Copyright 2014, Mihai Valentin
* http://www.mozilla.org/MPL/
*/
/*!
* based on
* Snowball JavaScript Library v0.3
* http://code.google.com/p/urim/
* http://snowball.tartarus.org/
*
* Copyright 2010, Oleg Mazko
* http://www.mozilla.org/MPL/
*/
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.da=function(){this.pipeline.reset(),this.pipeline.add(e.da.trimmer,e.da.stopWordFilter,e.da.stemmer),this.searchPipeline&&(this.searchPipeline.reset(),this.searchPipeline.add(e.da.stemmer))},e.da.wordCharacters="A-Za-zªºÀ-ÖØ-öø-ʸˠ-ˤᴀ-ᴥᴬ-ᵜᵢ-ᵥᵫ-ᵷᵹ-ᶾḀ-ỿⁱⁿₐ-ₜKÅℲⅎⅠ-ↈⱠ-ⱿꜢ-ꞇꞋ-ꞭꞰ-ꞷꟷ-ꟿꬰ-ꭚꭜ-ꭤff-stA-Za-z",e.da.trimmer=e.trimmerSupport.generateTrimmer(e.da.wordCharacters),e.Pipeline.registerFunction(e.da.trimmer,"trimmer-da"),e.da.stemmer=function(){var r=e.stemmerSupport.Among,i=e.stemmerSupport.SnowballProgram,n=new function(){function e(){var e,r=f.cursor+3;if(d=f.limit,0<=r&&r<=f.limit){for(a=r;;){if(e=f.cursor,f.in_grouping(w,97,248)){f.cursor=e;break}if(f.cursor=e,e>=f.limit)return;f.cursor++}for(;!f.out_grouping(w,97,248);){if(f.cursor>=f.limit)return;f.cursor++}d=f.cursor,d<a&&(d=a)}}function n(){var e,r;if(f.cursor>=d&&(r=f.limit_backward,f.limit_backward=d,f.ket=f.cursor,e=f.find_among_b(c,32),f.limit_backward=r,e))switch(f.bra=f.cursor,e){case 1:f.slice_del();break;case 2:f.in_grouping_b(p,97,229)&&f.slice_del()}}function t(){var e,r=f.limit-f.cursor;f.cursor>=d&&(e=f.limit_backward,f.limit_backward=d,f.ket=f.cursor,f.find_among_b(l,4)?(f.bra=f.cursor,f.limit_backward=e,f.cursor=f.limit-r,f.cursor>f.limit_backward&&(f.cursor--,f.bra=f.cursor,f.slice_del())):f.limit_backward=e)}function s(){var e,r,i,n=f.limit-f.cursor;if(f.ket=f.cursor,f.eq_s_b(2,"st")&&(f.bra=f.cursor,f.eq_s_b(2,"ig")&&f.slice_del()),f.cursor=f.limit-n,f.cursor>=d&&(r=f.limit_backward,f.limit_backward=d,f.ket=f.cursor,e=f.find_among_b(m,5),f.limit_backward=r,e))switch(f.bra=f.cursor,e){case 1:f.slice_del(),i=f.limit-f.cursor,t(),f.cursor=f.limit-i;break;case 2:f.slice_from("løs")}}function o(){var e;f.cursor>=d&&(e=f.limit_backward,f.limit_backward=d,f.ket=f.cursor,f.out_grouping_b(w,97,248)?(f.bra=f.cursor,u=f.slice_to(u),f.limit_backward=e,f.eq_v_b(u)&&f.slice_del()):f.limit_backward=e)}var a,d,u,c=[new r("hed",-1,1),new r("ethed",0,1),new r("ered",-1,1),new r("e",-1,1),new r("erede",3,1),new r("ende",3,1),new r("erende",5,1),new r("ene",3,1),new r("erne",3,1),new r("ere",3,1),new r("en",-1,1),new r("heden",10,1),new r("eren",10,1),new r("er",-1,1),new r("heder",13,1),new r("erer",13,1),new r("s",-1,2),new r("heds",16,1),new r("es",16,1),new r("endes",18,1),new r("erendes",19,1),new r("enes",18,1),new r("ernes",18,1),new r("eres",18,1),new r("ens",16,1),new r("hedens",24,1),new r("erens",24,1),new r("ers",16,1),new r("ets",16,1),new r("erets",28,1),new r("et",-1,1),new r("eret",30,1)],l=[new r("gd",-1,-1),new r("dt",-1,-1),new r("gt",-1,-1),new r("kt",-1,-1)],m=[new r("ig",-1,1),new r("lig",0,1),new r("elig",1,1),new r("els",-1,1),new r("løst",-1,2)],w=[17,65,16,1,0,0,0,0,0,0,0,0,0,0,0,0,48,0,128],p=[239,254,42,3,0,0,0,0,0,0,0,0,0,0,0,0,16],f=new i;this.setCurrent=function(e){f.setCurrent(e)},this.getCurrent=function(){return f.getCurrent()},this.stem=function(){var r=f.cursor;return e(),f.limit_backward=r,f.cursor=f.limit,n(),f.cursor=f.limit,t(),f.cursor=f.limit,s(),f.cursor=f.limit,o(),!0}};return function(e){return"function"==typeof e.update?e.update(function(e){return n.setCurrent(e),n.stem(),n.getCurrent()}):(n.setCurrent(e),n.stem(),n.getCurrent())}}(),e.Pipeline.registerFunction(e.da.stemmer,"stemmer-da"),e.da.stopWordFilter=e.generateStopWordFilter("ad af alle alt anden at blev blive bliver da de dem den denne der deres det dette dig din disse dog du efter eller en end er et for fra ham han hans har havde have hende hendes her hos hun hvad hvis hvor i ikke ind jeg jer jo kunne man mange med meget men mig min mine mit mod ned noget nogle nu når og også om op os over på selv sig sin sine sit skal skulle som sådan thi til ud under var vi vil ville vor være været".split(" ")),e.Pipeline.registerFunction(e.da.stopWordFilter,"stopWordFilter-da")}});
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
-1
View File
@@ -1 +0,0 @@
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.hi=function(){this.pipeline.reset(),this.pipeline.add(e.hi.trimmer,e.hi.stopWordFilter,e.hi.stemmer),this.searchPipeline&&(this.searchPipeline.reset(),this.searchPipeline.add(e.hi.stemmer))},e.hi.wordCharacters="ऀ-ःऄ-एऐ-टठ-यर-िी-ॏॐ-य़ॠ-९॰-ॿa-zA-Z-zA-0-9-",e.hi.trimmer=e.trimmerSupport.generateTrimmer(e.hi.wordCharacters),e.Pipeline.registerFunction(e.hi.trimmer,"trimmer-hi"),e.hi.stopWordFilter=e.generateStopWordFilter("अत अपना अपनी अपने अभी अंदर आदि आप इत्यादि इन इनका इन्हीं इन्हें इन्हों इस इसका इसकी इसके इसमें इसी इसे उन उनका उनकी उनके उनको उन्हीं उन्हें उन्हों उस उसके उसी उसे एक एवं एस ऐसे और कई कर करता करते करना करने करें कहते कहा का काफ़ी कि कितना किन्हें किन्हों किया किर किस किसी किसे की कुछ कुल के को कोई कौन कौनसा गया घर जब जहाँ जा जितना जिन जिन्हें जिन्हों जिस जिसे जीधर जैसा जैसे जो तक तब तरह तिन तिन्हें तिन्हों तिस तिसे तो था थी थे दबारा दिया दुसरा दूसरे दो द्वारा न नके नहीं ना निहायत नीचे ने पर पहले पूरा पे फिर बनी बही बहुत बाद बाला बिलकुल भी भीतर मगर मानो मे में यदि यह यहाँ यही या यिह ये रखें रहा रहे ऱ्वासा लिए लिये लेकिन व वग़ैरह वर्ग वह वहाँ वहीं वाले वुह वे वो सकता सकते सबसे सभी साथ साबुत साभ सारा से सो संग ही हुआ हुई हुए है हैं हो होता होती होते होना होने".split(" ")),e.hi.stemmer=function(){return function(e){return"function"==typeof e.update?e.update(function(e){return e}):e}}();var r=e.wordcut;r.init(),e.hi.tokenizer=function(i){if(!arguments.length||null==i||void 0==i)return[];if(Array.isArray(i))return i.map(function(r){return isLunr2?new e.Token(r.toLowerCase()):r.toLowerCase()});var t=i.toString().toLowerCase().replace(/^\s+/,"");return r.cut(t).split("|")},e.Pipeline.registerFunction(e.hi.stemmer,"stemmer-hi"),e.Pipeline.registerFunction(e.hi.stopWordFilter,"stopWordFilter-hi")}});
File diff suppressed because one or more lines are too long
-1
View File
@@ -1 +0,0 @@
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.hy=function(){this.pipeline.reset(),this.pipeline.add(e.hy.trimmer,e.hy.stopWordFilter)},e.hy.wordCharacters="[A-Za-z԰-֏ff-ﭏ]",e.hy.trimmer=e.trimmerSupport.generateTrimmer(e.hy.wordCharacters),e.Pipeline.registerFunction(e.hy.trimmer,"trimmer-hy"),e.hy.stopWordFilter=e.generateStopWordFilter("դու և եք էիր էիք հետո նաև նրանք որը վրա է որ պիտի են այս մեջ ն իր ու ի այդ որոնք այն կամ էր մի ես համար այլ իսկ էին ենք հետ ին թ էինք մենք նրա նա դուք եմ էի ըստ որպես ում".split(" ")),e.Pipeline.registerFunction(e.hy.stopWordFilter,"stopWordFilter-hy"),e.hy.stemmer=function(){return function(e){return"function"==typeof e.update?e.update(function(e){return e}):e}}(),e.Pipeline.registerFunction(e.hy.stemmer,"stemmer-hy")}});
File diff suppressed because one or more lines are too long
-1
View File
@@ -1 +0,0 @@
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");var r="2"==e.version[0];e.ja=function(){this.pipeline.reset(),this.pipeline.add(e.ja.trimmer,e.ja.stopWordFilter,e.ja.stemmer),r?this.tokenizer=e.ja.tokenizer:(e.tokenizer&&(e.tokenizer=e.ja.tokenizer),this.tokenizerFn&&(this.tokenizerFn=e.ja.tokenizer))};var t=new e.TinySegmenter;e.ja.tokenizer=function(i){var n,o,s,p,a,u,m,l,c,f;if(!arguments.length||null==i||void 0==i)return[];if(Array.isArray(i))return i.map(function(t){return r?new e.Token(t.toLowerCase()):t.toLowerCase()});for(o=i.toString().toLowerCase().replace(/^\s+/,""),n=o.length-1;n>=0;n--)if(/\S/.test(o.charAt(n))){o=o.substring(0,n+1);break}for(a=[],s=o.length,c=0,l=0;c<=s;c++)if(u=o.charAt(c),m=c-l,u.match(/\s/)||c==s){if(m>0)for(p=t.segment(o.slice(l,c)).filter(function(e){return!!e}),f=l,n=0;n<p.length;n++)r?a.push(new e.Token(p[n],{position:[f,p[n].length],index:a.length})):a.push(p[n]),f+=p[n].length;l=c+1}return a},e.ja.stemmer=function(){return function(e){return e}}(),e.Pipeline.registerFunction(e.ja.stemmer,"stemmer-ja"),e.ja.wordCharacters="一二三四五六七八九十百千万億兆一-龠々〆ヵヶぁ-んァ-ヴーア-ン゙a-zA-Z-zA-0-9-",e.ja.trimmer=e.trimmerSupport.generateTrimmer(e.ja.wordCharacters),e.Pipeline.registerFunction(e.ja.trimmer,"trimmer-ja"),e.ja.stopWordFilter=e.generateStopWordFilter("これ それ あれ この その あの ここ そこ あそこ こちら どこ だれ なに なん 何 私 貴方 貴方方 我々 私達 あの人 あのかた 彼女 彼 です あります おります います は が の に を で え から まで より も どの と し それで しかし".split(" ")),e.Pipeline.registerFunction(e.ja.stopWordFilter,"stopWordFilter-ja"),e.jp=e.ja,e.Pipeline.registerFunction(e.jp.stemmer,"stemmer-jp"),e.Pipeline.registerFunction(e.jp.trimmer,"trimmer-jp"),e.Pipeline.registerFunction(e.jp.stopWordFilter,"stopWordFilter-jp")}});
-1
View File
@@ -1 +0,0 @@
module.exports=require("./lunr.ja");
-1
View File
@@ -1 +0,0 @@
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.kn=function(){this.pipeline.reset(),this.pipeline.add(e.kn.trimmer,e.kn.stopWordFilter,e.kn.stemmer),this.searchPipeline&&(this.searchPipeline.reset(),this.searchPipeline.add(e.kn.stemmer))},e.kn.wordCharacters="ಀ-಄ಅ-ಔಕ-ಹಾ-ೌ಼-ಽೕ-ೖೝ-ೞೠ-ೡೢ-ೣ೤೥೦-೯ೱ-ೳ",e.kn.trimmer=e.trimmerSupport.generateTrimmer(e.kn.wordCharacters),e.Pipeline.registerFunction(e.kn.trimmer,"trimmer-kn"),e.kn.stopWordFilter=e.generateStopWordFilter("ಮತ್ತು ಈ ಒಂದು ರಲ್ಲಿ ಹಾಗೂ ಎಂದು ಅಥವಾ ಇದು ರ ಅವರು ಎಂಬ ಮೇಲೆ ಅವರ ತನ್ನ ಆದರೆ ತಮ್ಮ ನಂತರ ಮೂಲಕ ಹೆಚ್ಚು ನ ಆ ಕೆಲವು ಅನೇಕ ಎರಡು ಹಾಗು ಪ್ರಮುಖ ಇದನ್ನು ಇದರ ಸುಮಾರು ಅದರ ಅದು ಮೊದಲ ಬಗ್ಗೆ ನಲ್ಲಿ ರಂದು ಇತರ ಅತ್ಯಂತ ಹೆಚ್ಚಿನ ಸಹ ಸಾಮಾನ್ಯವಾಗಿ ನೇ ಹಲವಾರು ಹೊಸ ದಿ ಕಡಿಮೆ ಯಾವುದೇ ಹೊಂದಿದೆ ದೊಡ್ಡ ಅನ್ನು ಇವರು ಪ್ರಕಾರ ಇದೆ ಮಾತ್ರ ಕೂಡ ಇಲ್ಲಿ ಎಲ್ಲಾ ವಿವಿಧ ಅದನ್ನು ಹಲವು ರಿಂದ ಕೇವಲ ದ ದಕ್ಷಿಣ ಗೆ ಅವನ ಅತಿ ನೆಯ ಬಹಳ ಕೆಲಸ ಎಲ್ಲ ಪ್ರತಿ ಇತ್ಯಾದಿ ಇವು ಬೇರೆ ಹೀಗೆ ನಡುವೆ ಇದಕ್ಕೆ ಎಸ್ ಇವರ ಮೊದಲು ಶ್ರೀ ಮಾಡುವ ಇದರಲ್ಲಿ ರೀತಿಯ ಮಾಡಿದ ಕಾಲ ಅಲ್ಲಿ ಮಾಡಲು ಅದೇ ಈಗ ಅವು ಗಳು ಎ ಎಂಬುದು ಅವನು ಅಂದರೆ ಅವರಿಗೆ ಇರುವ ವಿಶೇಷ ಮುಂದೆ ಅವುಗಳ ಮುಂತಾದ ಮೂಲ ಬಿ ಮೀ ಒಂದೇ ಇನ್ನೂ ಹೆಚ್ಚಾಗಿ ಮಾಡಿ ಅವರನ್ನು ಇದೇ ಯ ರೀತಿಯಲ್ಲಿ ಜೊತೆ ಅದರಲ್ಲಿ ಮಾಡಿದರು ನಡೆದ ಆಗ ಮತ್ತೆ ಪೂರ್ವ ಆತ ಬಂದ ಯಾವ ಒಟ್ಟು ಇತರೆ ಹಿಂದೆ ಪ್ರಮಾಣದ ಗಳನ್ನು ಕುರಿತು ಯು ಆದ್ದರಿಂದ ಅಲ್ಲದೆ ನಗರದ ಮೇಲಿನ ಏಕೆಂದರೆ ರಷ್ಟು ಎಂಬುದನ್ನು ಬಾರಿ ಎಂದರೆ ಹಿಂದಿನ ಆದರೂ ಆದ ಸಂಬಂಧಿಸಿದ ಮತ್ತೊಂದು ಸಿ ಆತನ ".split(" ")),e.kn.stemmer=function(){return function(e){return"function"==typeof e.update?e.update(function(e){return e}):e}}();var r=e.wordcut;r.init(),e.kn.tokenizer=function(t){if(!arguments.length||null==t||void 0==t)return[];if(Array.isArray(t))return t.map(function(r){return isLunr2?new e.Token(r.toLowerCase()):r.toLowerCase()});var n=t.toString().toLowerCase().replace(/^\s+/,"");return r.cut(n).split("|")},e.Pipeline.registerFunction(e.kn.stemmer,"stemmer-kn"),e.Pipeline.registerFunction(e.kn.stopWordFilter,"stopWordFilter-kn")}});
File diff suppressed because one or more lines are too long
-1
View File
@@ -1 +0,0 @@
!function(e,t){"function"==typeof define&&define.amd?define(t):"object"==typeof exports?module.exports=t():t()(e.lunr)}(this,function(){return function(e){e.multiLanguage=function(){for(var t=Array.prototype.slice.call(arguments),i=t.join("-"),r="",n=[],s=[],p=0;p<t.length;++p)"en"==t[p]?(r+="\\w",n.unshift(e.stopWordFilter),n.push(e.stemmer),s.push(e.stemmer)):(r+=e[t[p]].wordCharacters,e[t[p]].stopWordFilter&&n.unshift(e[t[p]].stopWordFilter),e[t[p]].stemmer&&(n.push(e[t[p]].stemmer),s.push(e[t[p]].stemmer)));var o=e.trimmerSupport.generateTrimmer(r);return e.Pipeline.registerFunction(o,"lunr-multi-trimmer-"+i),n.unshift(o),function(){this.pipeline.reset(),this.pipeline.add.apply(this.pipeline,n),this.searchPipeline&&(this.searchPipeline.reset(),this.searchPipeline.add.apply(this.searchPipeline,s))}}}});
File diff suppressed because one or more lines are too long
-18
View File
@@ -1,18 +0,0 @@
/*!
* Lunr languages, `Norwegian` language
* https://github.com/MihaiValentin/lunr-languages
*
* Copyright 2014, Mihai Valentin
* http://www.mozilla.org/MPL/
*/
/*!
* based on
* Snowball JavaScript Library v0.3
* http://code.google.com/p/urim/
* http://snowball.tartarus.org/
*
* Copyright 2010, Oleg Mazko
* http://www.mozilla.org/MPL/
*/
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.no=function(){this.pipeline.reset(),this.pipeline.add(e.no.trimmer,e.no.stopWordFilter,e.no.stemmer),this.searchPipeline&&(this.searchPipeline.reset(),this.searchPipeline.add(e.no.stemmer))},e.no.wordCharacters="A-Za-zªºÀ-ÖØ-öø-ʸˠ-ˤᴀ-ᴥᴬ-ᵜᵢ-ᵥᵫ-ᵷᵹ-ᶾḀ-ỿⁱⁿₐ-ₜKÅℲⅎⅠ-ↈⱠ-ⱿꜢ-ꞇꞋ-ꞭꞰ-ꞷꟷ-ꟿꬰ-ꭚꭜ-ꭤff-stA-Za-z",e.no.trimmer=e.trimmerSupport.generateTrimmer(e.no.wordCharacters),e.Pipeline.registerFunction(e.no.trimmer,"trimmer-no"),e.no.stemmer=function(){var r=e.stemmerSupport.Among,n=e.stemmerSupport.SnowballProgram,i=new function(){function e(){var e,r=w.cursor+3;if(a=w.limit,0<=r||r<=w.limit){for(s=r;;){if(e=w.cursor,w.in_grouping(d,97,248)){w.cursor=e;break}if(e>=w.limit)return;w.cursor=e+1}for(;!w.out_grouping(d,97,248);){if(w.cursor>=w.limit)return;w.cursor++}a=w.cursor,a<s&&(a=s)}}function i(){var e,r,n;if(w.cursor>=a&&(r=w.limit_backward,w.limit_backward=a,w.ket=w.cursor,e=w.find_among_b(m,29),w.limit_backward=r,e))switch(w.bra=w.cursor,e){case 1:w.slice_del();break;case 2:n=w.limit-w.cursor,w.in_grouping_b(c,98,122)?w.slice_del():(w.cursor=w.limit-n,w.eq_s_b(1,"k")&&w.out_grouping_b(d,97,248)&&w.slice_del());break;case 3:w.slice_from("er")}}function t(){var e,r=w.limit-w.cursor;w.cursor>=a&&(e=w.limit_backward,w.limit_backward=a,w.ket=w.cursor,w.find_among_b(u,2)?(w.bra=w.cursor,w.limit_backward=e,w.cursor=w.limit-r,w.cursor>w.limit_backward&&(w.cursor--,w.bra=w.cursor,w.slice_del())):w.limit_backward=e)}function o(){var e,r;w.cursor>=a&&(r=w.limit_backward,w.limit_backward=a,w.ket=w.cursor,e=w.find_among_b(l,11),e?(w.bra=w.cursor,w.limit_backward=r,1==e&&w.slice_del()):w.limit_backward=r)}var s,a,m=[new r("a",-1,1),new r("e",-1,1),new r("ede",1,1),new r("ande",1,1),new r("ende",1,1),new r("ane",1,1),new r("ene",1,1),new r("hetene",6,1),new r("erte",1,3),new r("en",-1,1),new r("heten",9,1),new r("ar",-1,1),new r("er",-1,1),new r("heter",12,1),new r("s",-1,2),new r("as",14,1),new r("es",14,1),new r("edes",16,1),new r("endes",16,1),new r("enes",16,1),new r("hetenes",19,1),new r("ens",14,1),new r("hetens",21,1),new r("ers",14,1),new r("ets",14,1),new r("et",-1,1),new r("het",25,1),new r("ert",-1,3),new r("ast",-1,1)],u=[new r("dt",-1,-1),new r("vt",-1,-1)],l=[new r("leg",-1,1),new r("eleg",0,1),new r("ig",-1,1),new r("eig",2,1),new r("lig",2,1),new r("elig",4,1),new r("els",-1,1),new r("lov",-1,1),new r("elov",7,1),new r("slov",7,1),new r("hetslov",9,1)],d=[17,65,16,1,0,0,0,0,0,0,0,0,0,0,0,0,48,0,128],c=[119,125,149,1],w=new n;this.setCurrent=function(e){w.setCurrent(e)},this.getCurrent=function(){return w.getCurrent()},this.stem=function(){var r=w.cursor;return e(),w.limit_backward=r,w.cursor=w.limit,i(),w.cursor=w.limit,t(),w.cursor=w.limit,o(),!0}};return function(e){return"function"==typeof e.update?e.update(function(e){return i.setCurrent(e),i.stem(),i.getCurrent()}):(i.setCurrent(e),i.stem(),i.getCurrent())}}(),e.Pipeline.registerFunction(e.no.stemmer,"stemmer-no"),e.no.stopWordFilter=e.generateStopWordFilter("alle at av bare begge ble blei bli blir blitt både båe da de deg dei deim deira deires dem den denne der dere deres det dette di din disse ditt du dykk dykkar då eg ein eit eitt eller elles en enn er et ett etter for fordi fra før ha hadde han hans har hennar henne hennes her hjå ho hoe honom hoss hossen hun hva hvem hver hvilke hvilken hvis hvor hvordan hvorfor i ikke ikkje ikkje ingen ingi inkje inn inni ja jeg kan kom korleis korso kun kunne kva kvar kvarhelst kven kvi kvifor man mange me med medan meg meget mellom men mi min mine mitt mot mykje ned no noe noen noka noko nokon nokor nokre nå når og også om opp oss over på samme seg selv si si sia sidan siden sin sine sitt sjøl skal skulle slik so som som somme somt så sånn til um upp ut uten var vart varte ved vere verte vi vil ville vore vors vort vår være være vært å".split(" ")),e.Pipeline.registerFunction(e.no.stopWordFilter,"stopWordFilter-no")}});
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
-1
View File
@@ -1 +0,0 @@
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.sa=function(){this.pipeline.reset(),this.pipeline.add(e.sa.trimmer,e.sa.stopWordFilter,e.sa.stemmer),this.searchPipeline&&(this.searchPipeline.reset(),this.searchPipeline.add(e.sa.stemmer))},e.sa.wordCharacters="ऀ-ःऄ-एऐ-टठ-यर-िी-ॏॐ-य़ॠ-९॰-ॿ꣠-꣱ꣲ-ꣷ꣸-ꣻ꣼-ꣽꣾ-ꣿᆰ0-ᆰ9",e.sa.trimmer=e.trimmerSupport.generateTrimmer(e.sa.wordCharacters),e.Pipeline.registerFunction(e.sa.trimmer,"trimmer-sa"),e.sa.stopWordFilter=e.generateStopWordFilter('तथा अयम्‌ एकम्‌ इत्यस्मिन्‌ तथा तत्‌ वा अयम्‌ इत्यस्य ते आहूत उपरि तेषाम्‌ किन्तु तेषाम्‌ तदा इत्यनेन अधिकः इत्यस्य तत्‌ केचन बहवः द्वि तथा महत्वपूर्णः अयम्‌ अस्य विषये अयं अस्ति तत्‌ प्रथमः विषये इत्युपरि इत्युपरि इतर अधिकतमः अधिकः अपि सामान्यतया ठ इतरेतर नूतनम्‌ द न्यूनम्‌ कश्चित्‌ वा विशालः द सः अस्ति तदनुसारम् तत्र अस्ति केवलम्‌ अपि अत्र सर्वे विविधाः तत्‌ बहवः यतः इदानीम्‌ द दक्षिण इत्यस्मै तस्य उपरि नथ अतीव कार्यम्‌ सर्वे एकैकम्‌ इत्यादि। एते सन्ति उत इत्थम्‌ मध्ये एतदर्थं . स कस्य प्रथमः श्री. करोति अस्मिन् प्रकारः निर्मिता कालः तत्र कर्तुं समान अधुना ते सन्ति स एकः अस्ति सः अर्थात् तेषां कृते . स्थितम् विशेषः अग्रिम तेषाम्‌ समान स्रोतः ख म समान इदानीमपि अधिकतया करोतु ते समान इत्यस्य वीथी सह यस्मिन् कृतवान्‌ धृतः तदा पुनः पूर्वं सः आगतः किम्‌ कुल इतर पुरा मात्रा स विषये उ अतएव अपि नगरस्य उपरि यतः प्रतिशतं कतरः कालः साधनानि भूत तथापि जात सम्बन्धि अन्यत्‌ ग अतः अस्माकं स्वकीयाः अस्माकं इदानीं अन्तः इत्यादयः भवन्तः इत्यादयः एते एताः तस्य अस्य इदम् एते तेषां तेषां तेषां तान् तेषां तेषां तेषां समानः सः एकः च तादृशाः बहवः अन्ये च वदन्ति यत् कियत् कस्मै कस्मै यस्मै यस्मै यस्मै यस्मै न अतिनीचः किन्तु प्रथमं सम्पूर्णतया ततः चिरकालानन्तरं पुस्तकं सम्पूर्णतया अन्तः किन्तु अत्र वा इह इव श्रद्धाय अवशिष्यते परन्तु अन्ये वर्गाः सन्ति ते सन्ति शक्नुवन्ति सर्वे मिलित्वा सर्वे एकत्र"'.split(" ")),e.sa.stemmer=function(){return function(e){return"function"==typeof e.update?e.update(function(e){return e}):e}}();var r=e.wordcut;r.init(),e.sa.tokenizer=function(t){if(!arguments.length||null==t||void 0==t)return[];if(Array.isArray(t))return t.map(function(r){return isLunr2?new e.Token(r.toLowerCase()):r.toLowerCase()});var i=t.toString().toLowerCase().replace(/^\s+/,"");return r.cut(i).split("|")},e.Pipeline.registerFunction(e.sa.stemmer,"stemmer-sa"),e.Pipeline.registerFunction(e.sa.stopWordFilter,"stopWordFilter-sa")}});
@@ -1 +0,0 @@
!function(r,t){"function"==typeof define&&define.amd?define(t):"object"==typeof exports?module.exports=t():t()(r.lunr)}(this,function(){return function(r){r.stemmerSupport={Among:function(r,t,i,s){if(this.toCharArray=function(r){for(var t=r.length,i=new Array(t),s=0;s<t;s++)i[s]=r.charCodeAt(s);return i},!r&&""!=r||!t&&0!=t||!i)throw"Bad Among initialisation: s:"+r+", substring_i: "+t+", result: "+i;this.s_size=r.length,this.s=this.toCharArray(r),this.substring_i=t,this.result=i,this.method=s},SnowballProgram:function(){var r;return{bra:0,ket:0,limit:0,cursor:0,limit_backward:0,setCurrent:function(t){r=t,this.cursor=0,this.limit=t.length,this.limit_backward=0,this.bra=this.cursor,this.ket=this.limit},getCurrent:function(){var t=r;return r=null,t},in_grouping:function(t,i,s){if(this.cursor<this.limit){var e=r.charCodeAt(this.cursor);if(e<=s&&e>=i&&(e-=i,t[e>>3]&1<<(7&e)))return this.cursor++,!0}return!1},in_grouping_b:function(t,i,s){if(this.cursor>this.limit_backward){var e=r.charCodeAt(this.cursor-1);if(e<=s&&e>=i&&(e-=i,t[e>>3]&1<<(7&e)))return this.cursor--,!0}return!1},out_grouping:function(t,i,s){if(this.cursor<this.limit){var e=r.charCodeAt(this.cursor);if(e>s||e<i)return this.cursor++,!0;if(e-=i,!(t[e>>3]&1<<(7&e)))return this.cursor++,!0}return!1},out_grouping_b:function(t,i,s){if(this.cursor>this.limit_backward){var e=r.charCodeAt(this.cursor-1);if(e>s||e<i)return this.cursor--,!0;if(e-=i,!(t[e>>3]&1<<(7&e)))return this.cursor--,!0}return!1},eq_s:function(t,i){if(this.limit-this.cursor<t)return!1;for(var s=0;s<t;s++)if(r.charCodeAt(this.cursor+s)!=i.charCodeAt(s))return!1;return this.cursor+=t,!0},eq_s_b:function(t,i){if(this.cursor-this.limit_backward<t)return!1;for(var s=0;s<t;s++)if(r.charCodeAt(this.cursor-t+s)!=i.charCodeAt(s))return!1;return this.cursor-=t,!0},find_among:function(t,i){for(var s=0,e=i,n=this.cursor,u=this.limit,o=0,h=0,c=!1;;){for(var a=s+(e-s>>1),f=0,l=o<h?o:h,_=t[a],m=l;m<_.s_size;m++){if(n+l==u){f=-1;break}if(f=r.charCodeAt(n+l)-_.s[m])break;l++}if(f<0?(e=a,h=l):(s=a,o=l),e-s<=1){if(s>0||e==s||c)break;c=!0}}for(;;){var _=t[s];if(o>=_.s_size){if(this.cursor=n+_.s_size,!_.method)return _.result;var b=_.method();if(this.cursor=n+_.s_size,b)return _.result}if((s=_.substring_i)<0)return 0}},find_among_b:function(t,i){for(var s=0,e=i,n=this.cursor,u=this.limit_backward,o=0,h=0,c=!1;;){for(var a=s+(e-s>>1),f=0,l=o<h?o:h,_=t[a],m=_.s_size-1-l;m>=0;m--){if(n-l==u){f=-1;break}if(f=r.charCodeAt(n-1-l)-_.s[m])break;l++}if(f<0?(e=a,h=l):(s=a,o=l),e-s<=1){if(s>0||e==s||c)break;c=!0}}for(;;){var _=t[s];if(o>=_.s_size){if(this.cursor=n-_.s_size,!_.method)return _.result;var b=_.method();if(this.cursor=n-_.s_size,b)return _.result}if((s=_.substring_i)<0)return 0}},replace_s:function(t,i,s){var e=s.length-(i-t),n=r.substring(0,t),u=r.substring(i);return r=n+s+u,this.limit+=e,this.cursor>=i?this.cursor+=e:this.cursor>t&&(this.cursor=t),e},slice_check:function(){if(this.bra<0||this.bra>this.ket||this.ket>this.limit||this.limit>r.length)throw"faulty slice operation"},slice_from:function(r){this.slice_check(),this.replace_s(this.bra,this.ket,r)},slice_del:function(){this.slice_from("")},insert:function(r,t,i){var s=this.replace_s(r,t,i);r<=this.bra&&(this.bra+=s),r<=this.ket&&(this.ket+=s)},slice_to:function(){return this.slice_check(),r.substring(this.bra,this.ket)},eq_v_b:function(r){return this.eq_s_b(r.length,r)}}}},r.trimmerSupport={generateTrimmer:function(r){var t=new RegExp("^[^"+r+"]+"),i=new RegExp("[^"+r+"]+$");return function(r){return"function"==typeof r.update?r.update(function(r){return r.replace(t,"").replace(i,"")}):r.replace(t,"").replace(i,"")}}}}});
-18
View File
@@ -1,18 +0,0 @@
/*!
* Lunr languages, `Swedish` language
* https://github.com/MihaiValentin/lunr-languages
*
* Copyright 2014, Mihai Valentin
* http://www.mozilla.org/MPL/
*/
/*!
* based on
* Snowball JavaScript Library v0.3
* http://code.google.com/p/urim/
* http://snowball.tartarus.org/
*
* Copyright 2010, Oleg Mazko
* http://www.mozilla.org/MPL/
*/
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.sv=function(){this.pipeline.reset(),this.pipeline.add(e.sv.trimmer,e.sv.stopWordFilter,e.sv.stemmer),this.searchPipeline&&(this.searchPipeline.reset(),this.searchPipeline.add(e.sv.stemmer))},e.sv.wordCharacters="A-Za-zªºÀ-ÖØ-öø-ʸˠ-ˤᴀ-ᴥᴬ-ᵜᵢ-ᵥᵫ-ᵷᵹ-ᶾḀ-ỿⁱⁿₐ-ₜKÅℲⅎⅠ-ↈⱠ-ⱿꜢ-ꞇꞋ-ꞭꞰ-ꞷꟷ-ꟿꬰ-ꭚꭜ-ꭤff-stA-Za-z",e.sv.trimmer=e.trimmerSupport.generateTrimmer(e.sv.wordCharacters),e.Pipeline.registerFunction(e.sv.trimmer,"trimmer-sv"),e.sv.stemmer=function(){var r=e.stemmerSupport.Among,n=e.stemmerSupport.SnowballProgram,t=new function(){function e(){var e,r=w.cursor+3;if(o=w.limit,0<=r||r<=w.limit){for(a=r;;){if(e=w.cursor,w.in_grouping(l,97,246)){w.cursor=e;break}if(w.cursor=e,w.cursor>=w.limit)return;w.cursor++}for(;!w.out_grouping(l,97,246);){if(w.cursor>=w.limit)return;w.cursor++}o=w.cursor,o<a&&(o=a)}}function t(){var e,r=w.limit_backward;if(w.cursor>=o&&(w.limit_backward=o,w.cursor=w.limit,w.ket=w.cursor,e=w.find_among_b(u,37),w.limit_backward=r,e))switch(w.bra=w.cursor,e){case 1:w.slice_del();break;case 2:w.in_grouping_b(d,98,121)&&w.slice_del()}}function i(){var e=w.limit_backward;w.cursor>=o&&(w.limit_backward=o,w.cursor=w.limit,w.find_among_b(c,7)&&(w.cursor=w.limit,w.ket=w.cursor,w.cursor>w.limit_backward&&(w.bra=--w.cursor,w.slice_del())),w.limit_backward=e)}function s(){var e,r;if(w.cursor>=o){if(r=w.limit_backward,w.limit_backward=o,w.cursor=w.limit,w.ket=w.cursor,e=w.find_among_b(m,5))switch(w.bra=w.cursor,e){case 1:w.slice_del();break;case 2:w.slice_from("lös");break;case 3:w.slice_from("full")}w.limit_backward=r}}var a,o,u=[new r("a",-1,1),new r("arna",0,1),new r("erna",0,1),new r("heterna",2,1),new r("orna",0,1),new r("ad",-1,1),new r("e",-1,1),new r("ade",6,1),new r("ande",6,1),new r("arne",6,1),new r("are",6,1),new r("aste",6,1),new r("en",-1,1),new r("anden",12,1),new r("aren",12,1),new r("heten",12,1),new r("ern",-1,1),new r("ar",-1,1),new r("er",-1,1),new r("heter",18,1),new r("or",-1,1),new r("s",-1,2),new r("as",21,1),new r("arnas",22,1),new r("ernas",22,1),new r("ornas",22,1),new r("es",21,1),new r("ades",26,1),new r("andes",26,1),new r("ens",21,1),new r("arens",29,1),new r("hetens",29,1),new r("erns",21,1),new r("at",-1,1),new r("andet",-1,1),new r("het",-1,1),new r("ast",-1,1)],c=[new r("dd",-1,-1),new r("gd",-1,-1),new r("nn",-1,-1),new r("dt",-1,-1),new r("gt",-1,-1),new r("kt",-1,-1),new r("tt",-1,-1)],m=[new r("ig",-1,1),new r("lig",0,1),new r("els",-1,1),new r("fullt",-1,3),new r("löst",-1,2)],l=[17,65,16,1,0,0,0,0,0,0,0,0,0,0,0,0,24,0,32],d=[119,127,149],w=new n;this.setCurrent=function(e){w.setCurrent(e)},this.getCurrent=function(){return w.getCurrent()},this.stem=function(){var r=w.cursor;return e(),w.limit_backward=r,w.cursor=w.limit,t(),w.cursor=w.limit,i(),w.cursor=w.limit,s(),!0}};return function(e){return"function"==typeof e.update?e.update(function(e){return t.setCurrent(e),t.stem(),t.getCurrent()}):(t.setCurrent(e),t.stem(),t.getCurrent())}}(),e.Pipeline.registerFunction(e.sv.stemmer,"stemmer-sv"),e.sv.stopWordFilter=e.generateStopWordFilter("alla allt att av blev bli blir blivit de dem den denna deras dess dessa det detta dig din dina ditt du där då efter ej eller en er era ert ett från för ha hade han hans har henne hennes hon honom hur här i icke ingen inom inte jag ju kan kunde man med mellan men mig min mina mitt mot mycket ni nu när någon något några och om oss på samma sedan sig sin sina sitta själv skulle som så sådan sådana sådant till under upp ut utan vad var vara varför varit varje vars vart vem vi vid vilka vilkas vilken vilket vår våra vårt än är åt över".split(" ")),e.Pipeline.registerFunction(e.sv.stopWordFilter,"stopWordFilter-sv")}});
-1
View File
@@ -1 +0,0 @@
!function(e,t){"function"==typeof define&&define.amd?define(t):"object"==typeof exports?module.exports=t():t()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.ta=function(){this.pipeline.reset(),this.pipeline.add(e.ta.trimmer,e.ta.stopWordFilter,e.ta.stemmer),this.searchPipeline&&(this.searchPipeline.reset(),this.searchPipeline.add(e.ta.stemmer))},e.ta.wordCharacters="஀-உஊ-ஏஐ-ஙச-ட஠-னப-யர-ஹ஺-ிீ-௉ொ-௏ௐ-௙௚-௟௠-௩௪-௯௰-௹௺-௿a-zA-Z-zA-0-9-",e.ta.trimmer=e.trimmerSupport.generateTrimmer(e.ta.wordCharacters),e.Pipeline.registerFunction(e.ta.trimmer,"trimmer-ta"),e.ta.stopWordFilter=e.generateStopWordFilter("அங்கு அங்கே அது அதை அந்த அவர் அவர்கள் அவள் அவன் அவை ஆக ஆகவே ஆகையால் ஆதலால் ஆதலினால் ஆனாலும் ஆனால் இங்கு இங்கே இது இதை இந்த இப்படி இவர் இவர்கள் இவள் இவன் இவை இவ்வளவு உனக்கு உனது உன் உன்னால் எங்கு எங்கே எது எதை எந்த எப்படி எவர் எவர்கள் எவள் எவன் எவை எவ்வளவு எனக்கு எனது எனவே என் என்ன என்னால் ஏது ஏன் தனது தன்னால் தானே தான் நாங்கள் நாம் நான் நீ நீங்கள்".split(" ")),e.ta.stemmer=function(){return function(e){return"function"==typeof e.update?e.update(function(e){return e}):e}}();var t=e.wordcut;t.init(),e.ta.tokenizer=function(r){if(!arguments.length||null==r||void 0==r)return[];if(Array.isArray(r))return r.map(function(t){return isLunr2?new e.Token(t.toLowerCase()):t.toLowerCase()});var i=r.toString().toLowerCase().replace(/^\s+/,"");return t.cut(i).split("|")},e.Pipeline.registerFunction(e.ta.stemmer,"stemmer-ta"),e.Pipeline.registerFunction(e.ta.stopWordFilter,"stopWordFilter-ta")}});
-1
View File
@@ -1 +0,0 @@
!function(e,t){"function"==typeof define&&define.amd?define(t):"object"==typeof exports?module.exports=t():t()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.te=function(){this.pipeline.reset(),this.pipeline.add(e.te.trimmer,e.te.stopWordFilter,e.te.stemmer),this.searchPipeline&&(this.searchPipeline.reset(),this.searchPipeline.add(e.te.stemmer))},e.te.wordCharacters="ఀ-ఄఅ-ఔక-హా-ౌౕ-ౖౘ-ౚౠ-ౡౢ-ౣ౦-౯౸-౿఼ఽ్ౝ౷౤౥",e.te.trimmer=e.trimmerSupport.generateTrimmer(e.te.wordCharacters),e.Pipeline.registerFunction(e.te.trimmer,"trimmer-te"),e.te.stopWordFilter=e.generateStopWordFilter("అందరూ అందుబాటులో అడగండి అడగడం అడ్డంగా అనుగుణంగా అనుమతించు అనుమతిస్తుంది అయితే ఇప్పటికే ఉన్నారు ఎక్కడైనా ఎప్పుడు ఎవరైనా ఎవరో ఏ ఏదైనా ఏమైనప్పటికి ఒక ఒకరు కనిపిస్తాయి కాదు కూడా గా గురించి చుట్టూ చేయగలిగింది తగిన తర్వాత దాదాపు దూరంగా నిజంగా పై ప్రకారం ప్రక్కన మధ్య మరియు మరొక మళ్ళీ మాత్రమే మెచ్చుకో వద్ద వెంట వేరుగా వ్యతిరేకంగా సంబంధం".split(" ")),e.te.stemmer=function(){return function(e){return"function"==typeof e.update?e.update(function(e){return e}):e}}();var t=e.wordcut;t.init(),e.te.tokenizer=function(r){if(!arguments.length||null==r||void 0==r)return[];if(Array.isArray(r))return r.map(function(t){return isLunr2?new e.Token(t.toLowerCase()):t.toLowerCase()});var i=r.toString().toLowerCase().replace(/^\s+/,"");return t.cut(i).split("|")},e.Pipeline.registerFunction(e.te.stemmer,"stemmer-te"),e.Pipeline.registerFunction(e.te.stopWordFilter,"stopWordFilter-te")}});
-1
View File
@@ -1 +0,0 @@
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");var r="2"==e.version[0];e.th=function(){this.pipeline.reset(),this.pipeline.add(e.th.trimmer),r?this.tokenizer=e.th.tokenizer:(e.tokenizer&&(e.tokenizer=e.th.tokenizer),this.tokenizerFn&&(this.tokenizerFn=e.th.tokenizer))},e.th.wordCharacters="[฀-๿]",e.th.trimmer=e.trimmerSupport.generateTrimmer(e.th.wordCharacters),e.Pipeline.registerFunction(e.th.trimmer,"trimmer-th");var t=e.wordcut;t.init(),e.th.tokenizer=function(i){if(!arguments.length||null==i||void 0==i)return[];if(Array.isArray(i))return i.map(function(t){return r?new e.Token(t):t});var n=i.toString().replace(/^\s+/,"");return t.cut(n).split("|")}}});
File diff suppressed because one or more lines are too long
-1
View File
@@ -1 +0,0 @@
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r():r()(e.lunr)}(this,function(){return function(e){if(void 0===e)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===e.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");e.vi=function(){this.pipeline.reset(),this.pipeline.add(e.vi.stopWordFilter,e.vi.trimmer)},e.vi.wordCharacters="[A-Za-ẓ̀͐́͑̉̃̓ÂâÊêÔôĂ-ăĐ-đƠ-ơƯ-ư]",e.vi.trimmer=e.trimmerSupport.generateTrimmer(e.vi.wordCharacters),e.Pipeline.registerFunction(e.vi.trimmer,"trimmer-vi"),e.vi.stopWordFilter=e.generateStopWordFilter("là cái nhưng mà".split(" "))}});
-1
View File
@@ -1 +0,0 @@
!function(e,r){"function"==typeof define&&define.amd?define(r):"object"==typeof exports?module.exports=r(require("@node-rs/jieba")):r()(e.lunr)}(this,function(e){return function(r,t){if(void 0===r)throw new Error("Lunr is not present. Please include / require Lunr before this script.");if(void 0===r.stemmerSupport)throw new Error("Lunr stemmer support is not present. Please include / require Lunr stemmer support before this script.");var i="2"==r.version[0];r.zh=function(){this.pipeline.reset(),this.pipeline.add(r.zh.trimmer,r.zh.stopWordFilter,r.zh.stemmer),i?this.tokenizer=r.zh.tokenizer:(r.tokenizer&&(r.tokenizer=r.zh.tokenizer),this.tokenizerFn&&(this.tokenizerFn=r.zh.tokenizer))},r.zh.tokenizer=function(n){if(!arguments.length||null==n||void 0==n)return[];if(Array.isArray(n))return n.map(function(e){return i?new r.Token(e.toLowerCase()):e.toLowerCase()});t&&e.load(t);var o=n.toString().trim().toLowerCase(),s=[];e.cut(o,!0).forEach(function(e){s=s.concat(e.split(" "))}),s=s.filter(function(e){return!!e});var u=0;return s.map(function(e,t){if(i){var n=o.indexOf(e,u),s={};return s.position=[n,e.length],s.index=t,u=n,new r.Token(e,s)}return e})},r.zh.wordCharacters="\\w一-龥",r.zh.trimmer=r.trimmerSupport.generateTrimmer(r.zh.wordCharacters),r.Pipeline.registerFunction(r.zh.trimmer,"trimmer-zh"),r.zh.stemmer=function(){return function(e){return e}}(),r.Pipeline.registerFunction(r.zh.stemmer,"stemmer-zh"),r.zh.stopWordFilter=r.generateStopWordFilter("的 一 不 在 人 有 是 为 為 以 于 於 上 他 而 后 後 之 来 來 及 了 因 下 可 到 由 这 這 与 與 也 此 但 并 並 个 個 其 已 无 無 小 我 们 們 起 最 再 今 去 好 只 又 或 很 亦 某 把 那 你 乃 它 吧 被 比 别 趁 当 當 从 從 得 打 凡 儿 兒 尔 爾 该 該 各 给 給 跟 和 何 还 還 即 几 幾 既 看 据 據 距 靠 啦 另 么 麽 每 嘛 拿 哪 您 凭 憑 且 却 卻 让 讓 仍 啥 如 若 使 谁 誰 虽 雖 随 隨 同 所 她 哇 嗡 往 些 向 沿 哟 喲 用 咱 则 則 怎 曾 至 致 着 著 诸 諸 自".split(" ")),r.Pipeline.registerFunction(r.zh.stopWordFilter,"stopWordFilter-zh")}});
-206
View File
@@ -1,206 +0,0 @@
/**
* export the module via AMD, CommonJS or as a browser global
* Export code from https://github.com/umdjs/umd/blob/master/returnExports.js
*/
;(function (root, factory) {
if (typeof define === 'function' && define.amd) {
// AMD. Register as an anonymous module.
define(factory)
} else if (typeof exports === 'object') {
/**
* Node. Does not work with strict CommonJS, but
* only CommonJS-like environments that support module.exports,
* like Node.
*/
module.exports = factory()
} else {
// Browser globals (root is window)
factory()(root.lunr);
}
}(this, function () {
/**
* Just return a value to define the module export.
* This example returns an object, but the module
* can return a function as the exported value.
*/
return function(lunr) {
// TinySegmenter 0.1 -- Super compact Japanese tokenizer in Javascript
// (c) 2008 Taku Kudo <taku@chasen.org>
// TinySegmenter is freely distributable under the terms of a new BSD licence.
// For details, see http://chasen.org/~taku/software/TinySegmenter/LICENCE.txt
function TinySegmenter() {
var patterns = {
"[一二三四五六七八九十百千万億兆]":"M",
"[一-龠々〆ヵヶ]":"H",
"[ぁ-ん]":"I",
"[ァ-ヴーア-ン゙ー]":"K",
"[a-zA-Z-zA-]":"A",
"[0-9-]":"N"
}
this.chartype_ = [];
for (var i in patterns) {
var regexp = new RegExp(i);
this.chartype_.push([regexp, patterns[i]]);
}
this.BIAS__ = -332
this.BC1__ = {"HH":6,"II":2461,"KH":406,"OH":-1378};
this.BC2__ = {"AA":-3267,"AI":2744,"AN":-878,"HH":-4070,"HM":-1711,"HN":4012,"HO":3761,"IA":1327,"IH":-1184,"II":-1332,"IK":1721,"IO":5492,"KI":3831,"KK":-8741,"MH":-3132,"MK":3334,"OO":-2920};
this.BC3__ = {"HH":996,"HI":626,"HK":-721,"HN":-1307,"HO":-836,"IH":-301,"KK":2762,"MK":1079,"MM":4034,"OA":-1652,"OH":266};
this.BP1__ = {"BB":295,"OB":304,"OO":-125,"UB":352};
this.BP2__ = {"BO":60,"OO":-1762};
this.BQ1__ = {"BHH":1150,"BHM":1521,"BII":-1158,"BIM":886,"BMH":1208,"BNH":449,"BOH":-91,"BOO":-2597,"OHI":451,"OIH":-296,"OKA":1851,"OKH":-1020,"OKK":904,"OOO":2965};
this.BQ2__ = {"BHH":118,"BHI":-1159,"BHM":466,"BIH":-919,"BKK":-1720,"BKO":864,"OHH":-1139,"OHM":-181,"OIH":153,"UHI":-1146};
this.BQ3__ = {"BHH":-792,"BHI":2664,"BII":-299,"BKI":419,"BMH":937,"BMM":8335,"BNN":998,"BOH":775,"OHH":2174,"OHM":439,"OII":280,"OKH":1798,"OKI":-793,"OKO":-2242,"OMH":-2402,"OOO":11699};
this.BQ4__ = {"BHH":-3895,"BIH":3761,"BII":-4654,"BIK":1348,"BKK":-1806,"BMI":-3385,"BOO":-12396,"OAH":926,"OHH":266,"OHK":-2036,"ONN":-973};
this.BW1__ = {",と":660,",同":727,"B1あ":1404,"B1同":542,"、と":660,"、同":727,"」と":1682,"あっ":1505,"いう":1743,"いっ":-2055,"いる":672,"うし":-4817,"うん":665,"から":3472,"がら":600,"こう":-790,"こと":2083,"こん":-1262,"さら":-4143,"さん":4573,"した":2641,"して":1104,"すで":-3399,"そこ":1977,"それ":-871,"たち":1122,"ため":601,"った":3463,"つい":-802,"てい":805,"てき":1249,"でき":1127,"です":3445,"では":844,"とい":-4915,"とみ":1922,"どこ":3887,"ない":5713,"なっ":3015,"など":7379,"なん":-1113,"にし":2468,"には":1498,"にも":1671,"に対":-912,"の一":-501,"の中":741,"ませ":2448,"まで":1711,"まま":2600,"まる":-2155,"やむ":-1947,"よっ":-2565,"れた":2369,"れで":-913,"をし":1860,"を見":731,"亡く":-1886,"京都":2558,"取り":-2784,"大き":-2604,"大阪":1497,"平方":-2314,"引き":-1336,"日本":-195,"本当":-2423,"毎日":-2113,"目指":-724,"B1あ":1404,"B1同":542,"」と":1682};
this.BW2__ = {"..":-11822,"11":-669,"――":-5730,"−−":-13175,"いう":-1609,"うか":2490,"かし":-1350,"かも":-602,"から":-7194,"かれ":4612,"がい":853,"がら":-3198,"きた":1941,"くな":-1597,"こと":-8392,"この":-4193,"させ":4533,"され":13168,"さん":-3977,"しい":-1819,"しか":-545,"した":5078,"して":972,"しな":939,"その":-3744,"たい":-1253,"たた":-662,"ただ":-3857,"たち":-786,"たと":1224,"たは":-939,"った":4589,"って":1647,"っと":-2094,"てい":6144,"てき":3640,"てく":2551,"ては":-3110,"ても":-3065,"でい":2666,"でき":-1528,"でし":-3828,"です":-4761,"でも":-4203,"とい":1890,"とこ":-1746,"とと":-2279,"との":720,"とみ":5168,"とも":-3941,"ない":-2488,"なが":-1313,"など":-6509,"なの":2614,"なん":3099,"にお":-1615,"にし":2748,"にな":2454,"によ":-7236,"に対":-14943,"に従":-4688,"に関":-11388,"のか":2093,"ので":-7059,"のに":-6041,"のの":-6125,"はい":1073,"はが":-1033,"はず":-2532,"ばれ":1813,"まし":-1316,"まで":-6621,"まれ":5409,"めて":-3153,"もい":2230,"もの":-10713,"らか":-944,"らし":-1611,"らに":-1897,"りし":651,"りま":1620,"れた":4270,"れて":849,"れば":4114,"ろう":6067,"われ":7901,"を通":-11877,"んだ":728,"んな":-4115,"一人":602,"一方":-1375,"一日":970,"一部":-1051,"上が":-4479,"会社":-1116,"出て":2163,"分の":-7758,"同党":970,"同日":-913,"大阪":-2471,"委員":-1250,"少な":-1050,"年度":-8669,"年間":-1626,"府県":-2363,"手権":-1982,"新聞":-4066,"日新":-722,"日本":-7068,"日米":3372,"曜日":-601,"朝鮮":-2355,"本人":-2697,"東京":-1543,"然と":-1384,"社会":-1276,"立て":-990,"第に":-1612,"米国":-4268,"11":-669};
this.BW3__ = {"あた":-2194,"あり":719,"ある":3846,"い.":-1185,"い。":-1185,"いい":5308,"いえ":2079,"いく":3029,"いた":2056,"いっ":1883,"いる":5600,"いわ":1527,"うち":1117,"うと":4798,"えと":1454,"か.":2857,"か。":2857,"かけ":-743,"かっ":-4098,"かに":-669,"から":6520,"かり":-2670,"が,":1816,"が、":1816,"がき":-4855,"がけ":-1127,"がっ":-913,"がら":-4977,"がり":-2064,"きた":1645,"けど":1374,"こと":7397,"この":1542,"ころ":-2757,"さい":-714,"さを":976,"し,":1557,"し、":1557,"しい":-3714,"した":3562,"して":1449,"しな":2608,"しま":1200,"す.":-1310,"す。":-1310,"する":6521,"ず,":3426,"ず、":3426,"ずに":841,"そう":428,"た.":8875,"た。":8875,"たい":-594,"たの":812,"たり":-1183,"たる":-853,"だ.":4098,"だ。":4098,"だっ":1004,"った":-4748,"って":300,"てい":6240,"てお":855,"ても":302,"です":1437,"でに":-1482,"では":2295,"とう":-1387,"とし":2266,"との":541,"とも":-3543,"どう":4664,"ない":1796,"なく":-903,"など":2135,"に,":-1021,"に、":-1021,"にし":1771,"にな":1906,"には":2644,"の,":-724,"の、":-724,"の子":-1000,"は,":1337,"は、":1337,"べき":2181,"まし":1113,"ます":6943,"まっ":-1549,"まで":6154,"まれ":-793,"らし":1479,"られ":6820,"るる":3818,"れ,":854,"れ、":854,"れた":1850,"れて":1375,"れば":-3246,"れる":1091,"われ":-605,"んだ":606,"んで":798,"カ月":990,"会議":860,"入り":1232,"大会":2217,"始め":1681,"市":965,"新聞":-5055,"日,":974,"日、":974,"社会":2024,"カ月":990};
this.TC1__ = {"AAA":1093,"HHH":1029,"HHM":580,"HII":998,"HOH":-390,"HOM":-331,"IHI":1169,"IOH":-142,"IOI":-1015,"IOM":467,"MMH":187,"OOI":-1832};
this.TC2__ = {"HHO":2088,"HII":-1023,"HMM":-1154,"IHI":-1965,"KKH":703,"OII":-2649};
this.TC3__ = {"AAA":-294,"HHH":346,"HHI":-341,"HII":-1088,"HIK":731,"HOH":-1486,"IHH":128,"IHI":-3041,"IHO":-1935,"IIH":-825,"IIM":-1035,"IOI":-542,"KHH":-1216,"KKA":491,"KKH":-1217,"KOK":-1009,"MHH":-2694,"MHM":-457,"MHO":123,"MMH":-471,"NNH":-1689,"NNO":662,"OHO":-3393};
this.TC4__ = {"HHH":-203,"HHI":1344,"HHK":365,"HHM":-122,"HHN":182,"HHO":669,"HIH":804,"HII":679,"HOH":446,"IHH":695,"IHO":-2324,"IIH":321,"III":1497,"IIO":656,"IOO":54,"KAK":4845,"KKA":3386,"KKK":3065,"MHH":-405,"MHI":201,"MMH":-241,"MMM":661,"MOM":841};
this.TQ1__ = {"BHHH":-227,"BHHI":316,"BHIH":-132,"BIHH":60,"BIII":1595,"BNHH":-744,"BOHH":225,"BOOO":-908,"OAKK":482,"OHHH":281,"OHIH":249,"OIHI":200,"OIIH":-68};
this.TQ2__ = {"BIHH":-1401,"BIII":-1033,"BKAK":-543,"BOOO":-5591};
this.TQ3__ = {"BHHH":478,"BHHM":-1073,"BHIH":222,"BHII":-504,"BIIH":-116,"BIII":-105,"BMHI":-863,"BMHM":-464,"BOMH":620,"OHHH":346,"OHHI":1729,"OHII":997,"OHMH":481,"OIHH":623,"OIIH":1344,"OKAK":2792,"OKHH":587,"OKKA":679,"OOHH":110,"OOII":-685};
this.TQ4__ = {"BHHH":-721,"BHHM":-3604,"BHII":-966,"BIIH":-607,"BIII":-2181,"OAAA":-2763,"OAKK":180,"OHHH":-294,"OHHI":2446,"OHHO":480,"OHIH":-1573,"OIHH":1935,"OIHI":-493,"OIIH":626,"OIII":-4007,"OKAK":-8156};
this.TW1__ = {"につい":-4681,"東京都":2026};
this.TW2__ = {"ある程":-2049,"いった":-1256,"ころが":-2434,"しょう":3873,"その後":-4430,"だって":-1049,"ていた":1833,"として":-4657,"ともに":-4517,"もので":1882,"一気に":-792,"初めて":-1512,"同時に":-8097,"大きな":-1255,"対して":-2721,"社会党":-3216};
this.TW3__ = {"いただ":-1734,"してい":1314,"として":-4314,"につい":-5483,"にとっ":-5989,"に当た":-6247,"ので,":-727,"ので、":-727,"のもの":-600,"れから":-3752,"十二月":-2287};
this.TW4__ = {"いう.":8576,"いう。":8576,"からな":-2348,"してい":2958,"たが,":1516,"たが、":1516,"ている":1538,"という":1349,"ました":5543,"ません":1097,"ようと":-4258,"よると":5865};
this.UC1__ = {"A":484,"K":93,"M":645,"O":-505};
this.UC2__ = {"A":819,"H":1059,"I":409,"M":3987,"N":5775,"O":646};
this.UC3__ = {"A":-1370,"I":2311};
this.UC4__ = {"A":-2643,"H":1809,"I":-1032,"K":-3450,"M":3565,"N":3876,"O":6646};
this.UC5__ = {"H":313,"I":-1238,"K":-799,"M":539,"O":-831};
this.UC6__ = {"H":-506,"I":-253,"K":87,"M":247,"O":-387};
this.UP1__ = {"O":-214};
this.UP2__ = {"B":69,"O":935};
this.UP3__ = {"B":189};
this.UQ1__ = {"BH":21,"BI":-12,"BK":-99,"BN":142,"BO":-56,"OH":-95,"OI":477,"OK":410,"OO":-2422};
this.UQ2__ = {"BH":216,"BI":113,"OK":1759};
this.UQ3__ = {"BA":-479,"BH":42,"BI":1913,"BK":-7198,"BM":3160,"BN":6427,"BO":14761,"OI":-827,"ON":-3212};
this.UW1__ = {",":156,"、":156,"「":-463,"あ":-941,"う":-127,"が":-553,"き":121,"こ":505,"で":-201,"と":-547,"ど":-123,"に":-789,"の":-185,"は":-847,"も":-466,"や":-470,"よ":182,"ら":-292,"り":208,"れ":169,"を":-446,"ん":-137,"・":-135,"主":-402,"京":-268,"区":-912,"午":871,"国":-460,"大":561,"委":729,"市":-411,"日":-141,"理":361,"生":-408,"県":-386,"都":-718,"「":-463,"・":-135};
this.UW2__ = {",":-829,"、":-829,"":892,"「":-645,"」":3145,"あ":-538,"い":505,"う":134,"お":-502,"か":1454,"が":-856,"く":-412,"こ":1141,"さ":878,"ざ":540,"し":1529,"す":-675,"せ":300,"そ":-1011,"た":188,"だ":1837,"つ":-949,"て":-291,"で":-268,"と":-981,"ど":1273,"な":1063,"に":-1764,"の":130,"は":-409,"ひ":-1273,"べ":1261,"ま":600,"も":-1263,"や":-402,"よ":1639,"り":-579,"る":-694,"れ":571,"を":-2516,"ん":2095,"ア":-587,"カ":306,"キ":568,"ッ":831,"三":-758,"不":-2150,"世":-302,"中":-968,"主":-861,"事":492,"人":-123,"会":978,"保":362,"入":548,"初":-3025,"副":-1566,"北":-3414,"区":-422,"大":-1769,"天":-865,"太":-483,"子":-1519,"学":760,"実":1023,"小":-2009,"市":-813,"年":-1060,"強":1067,"手":-1519,"揺":-1033,"政":1522,"文":-1355,"新":-1682,"日":-1815,"明":-1462,"最":-630,"朝":-1843,"本":-1650,"東":-931,"果":-665,"次":-2378,"民":-180,"気":-1740,"理":752,"発":529,"目":-1584,"相":-242,"県":-1165,"立":-763,"第":810,"米":509,"自":-1353,"行":838,"西":-744,"見":-3874,"調":1010,"議":1198,"込":3041,"開":1758,"間":-1257,"「":-645,"」":3145,"ッ":831,"ア":-587,"カ":306,"キ":568};
this.UW3__ = {",":4889,"1":-800,"":-1723,"、":4889,"々":-2311,"":5827,"」":2670,"〓":-3573,"あ":-2696,"い":1006,"う":2342,"え":1983,"お":-4864,"か":-1163,"が":3271,"く":1004,"け":388,"げ":401,"こ":-3552,"ご":-3116,"さ":-1058,"し":-395,"す":584,"せ":3685,"そ":-5228,"た":842,"ち":-521,"っ":-1444,"つ":-1081,"て":6167,"で":2318,"と":1691,"ど":-899,"な":-2788,"に":2745,"の":4056,"は":4555,"ひ":-2171,"ふ":-1798,"へ":1199,"ほ":-5516,"ま":-4384,"み":-120,"め":1205,"も":2323,"や":-788,"よ":-202,"ら":727,"り":649,"る":5905,"れ":2773,"わ":-1207,"を":6620,"ん":-518,"ア":551,"グ":1319,"ス":874,"ッ":-1350,"ト":521,"ム":1109,"ル":1591,"ロ":2201,"ン":278,"・":-3794,"一":-1619,"下":-1759,"世":-2087,"両":3815,"中":653,"主":-758,"予":-1193,"二":974,"人":2742,"今":792,"他":1889,"以":-1368,"低":811,"何":4265,"作":-361,"保":-2439,"元":4858,"党":3593,"全":1574,"公":-3030,"六":755,"共":-1880,"円":5807,"再":3095,"分":457,"初":2475,"別":1129,"前":2286,"副":4437,"力":365,"動":-949,"務":-1872,"化":1327,"北":-1038,"区":4646,"千":-2309,"午":-783,"協":-1006,"口":483,"右":1233,"各":3588,"合":-241,"同":3906,"和":-837,"員":4513,"国":642,"型":1389,"場":1219,"外":-241,"妻":2016,"学":-1356,"安":-423,"実":-1008,"家":1078,"小":-513,"少":-3102,"州":1155,"市":3197,"平":-1804,"年":2416,"広":-1030,"府":1605,"度":1452,"建":-2352,"当":-3885,"得":1905,"思":-1291,"性":1822,"戸":-488,"指":-3973,"政":-2013,"教":-1479,"数":3222,"文":-1489,"新":1764,"日":2099,"旧":5792,"昨":-661,"時":-1248,"曜":-951,"最":-937,"月":4125,"期":360,"李":3094,"村":364,"東":-805,"核":5156,"森":2438,"業":484,"氏":2613,"民":-1694,"決":-1073,"法":1868,"海":-495,"無":979,"物":461,"特":-3850,"生":-273,"用":914,"町":1215,"的":7313,"直":-1835,"省":792,"県":6293,"知":-1528,"私":4231,"税":401,"立":-960,"第":1201,"米":7767,"系":3066,"約":3663,"級":1384,"統":-4229,"総":1163,"線":1255,"者":6457,"能":725,"自":-2869,"英":785,"見":1044,"調":-562,"財":-733,"費":1777,"車":1835,"軍":1375,"込":-1504,"通":-1136,"選":-681,"郎":1026,"郡":4404,"部":1200,"金":2163,"長":421,"開":-1432,"間":1302,"関":-1282,"雨":2009,"電":-1045,"非":2066,"駅":1620,"":-800,"」":2670,"・":-3794,"ッ":-1350,"ア":551,"グ":1319,"ス":874,"ト":521,"ム":1109,"ル":1591,"ロ":2201,"ン":278};
this.UW4__ = {",":3930,".":3508,"―":-4841,"、":3930,"。":3508,"":4999,"「":1895,"」":3798,"〓":-5156,"あ":4752,"い":-3435,"う":-640,"え":-2514,"お":2405,"か":530,"が":6006,"き":-4482,"ぎ":-3821,"く":-3788,"け":-4376,"げ":-4734,"こ":2255,"ご":1979,"さ":2864,"し":-843,"じ":-2506,"す":-731,"ず":1251,"せ":181,"そ":4091,"た":5034,"だ":5408,"ち":-3654,"っ":-5882,"つ":-1659,"て":3994,"で":7410,"と":4547,"な":5433,"に":6499,"ぬ":1853,"ね":1413,"の":7396,"は":8578,"ば":1940,"ひ":4249,"び":-4134,"ふ":1345,"へ":6665,"べ":-744,"ほ":1464,"ま":1051,"み":-2082,"む":-882,"め":-5046,"も":4169,"ゃ":-2666,"や":2795,"ょ":-1544,"よ":3351,"ら":-2922,"り":-9726,"る":-14896,"れ":-2613,"ろ":-4570,"わ":-1783,"を":13150,"ん":-2352,"カ":2145,"コ":1789,"セ":1287,"ッ":-724,"ト":-403,"メ":-1635,"ラ":-881,"リ":-541,"ル":-856,"ン":-3637,"・":-4371,"ー":-11870,"一":-2069,"中":2210,"予":782,"事":-190,"井":-1768,"人":1036,"以":544,"会":950,"体":-1286,"作":530,"側":4292,"先":601,"党":-2006,"共":-1212,"内":584,"円":788,"初":1347,"前":1623,"副":3879,"力":-302,"動":-740,"務":-2715,"化":776,"区":4517,"協":1013,"参":1555,"合":-1834,"和":-681,"員":-910,"器":-851,"回":1500,"国":-619,"園":-1200,"地":866,"場":-1410,"塁":-2094,"士":-1413,"多":1067,"大":571,"子":-4802,"学":-1397,"定":-1057,"寺":-809,"小":1910,"屋":-1328,"山":-1500,"島":-2056,"川":-2667,"市":2771,"年":374,"庁":-4556,"後":456,"性":553,"感":916,"所":-1566,"支":856,"改":787,"政":2182,"教":704,"文":522,"方":-856,"日":1798,"時":1829,"最":845,"月":-9066,"木":-485,"来":-442,"校":-360,"業":-1043,"氏":5388,"民":-2716,"気":-910,"沢":-939,"済":-543,"物":-735,"率":672,"球":-1267,"生":-1286,"産":-1101,"田":-2900,"町":1826,"的":2586,"目":922,"省":-3485,"県":2997,"空":-867,"立":-2112,"第":788,"米":2937,"系":786,"約":2171,"経":1146,"統":-1169,"総":940,"線":-994,"署":749,"者":2145,"能":-730,"般":-852,"行":-792,"規":792,"警":-1184,"議":-244,"谷":-1000,"賞":730,"車":-1481,"軍":1158,"輪":-1433,"込":-3370,"近":929,"道":-1291,"選":2596,"郎":-4866,"都":1192,"野":-1100,"銀":-2213,"長":357,"間":-2344,"院":-2297,"際":-2604,"電":-878,"領":-1659,"題":-792,"館":-1984,"首":1749,"高":2120,"「":1895,"」":3798,"・":-4371,"ッ":-724,"ー":-11870,"カ":2145,"コ":1789,"セ":1287,"ト":-403,"メ":-1635,"ラ":-881,"リ":-541,"ル":-856,"ン":-3637};
this.UW5__ = {",":465,".":-299,"1":-514,"E2":-32768,"]":-2762,"、":465,"。":-299,"「":363,"あ":1655,"い":331,"う":-503,"え":1199,"お":527,"か":647,"が":-421,"き":1624,"ぎ":1971,"く":312,"げ":-983,"さ":-1537,"し":-1371,"す":-852,"だ":-1186,"ち":1093,"っ":52,"つ":921,"て":-18,"で":-850,"と":-127,"ど":1682,"な":-787,"に":-1224,"の":-635,"は":-578,"べ":1001,"み":502,"め":865,"ゃ":3350,"ょ":854,"り":-208,"る":429,"れ":504,"わ":419,"を":-1264,"ん":327,"イ":241,"ル":451,"ン":-343,"中":-871,"京":722,"会":-1153,"党":-654,"務":3519,"区":-901,"告":848,"員":2104,"大":-1296,"学":-548,"定":1785,"嵐":-1304,"市":-2991,"席":921,"年":1763,"思":872,"所":-814,"挙":1618,"新":-1682,"日":218,"月":-4353,"査":932,"格":1356,"機":-1508,"氏":-1347,"田":240,"町":-3912,"的":-3149,"相":1319,"省":-1052,"県":-4003,"研":-997,"社":-278,"空":-813,"統":1955,"者":-2233,"表":663,"語":-1073,"議":1219,"選":-1018,"郎":-368,"長":786,"間":1191,"題":2368,"館":-689,"":-514,"E2":-32768,"「":363,"イ":241,"ル":451,"ン":-343};
this.UW6__ = {",":227,".":808,"1":-270,"E1":306,"、":227,"。":808,"あ":-307,"う":189,"か":241,"が":-73,"く":-121,"こ":-200,"じ":1782,"す":383,"た":-428,"っ":573,"て":-1014,"で":101,"と":-105,"な":-253,"に":-149,"の":-417,"は":-236,"も":-206,"り":187,"る":-135,"を":195,"ル":-673,"ン":-496,"一":-277,"中":201,"件":-800,"会":624,"前":302,"区":1792,"員":-1212,"委":798,"学":-960,"市":887,"広":-695,"後":535,"業":-697,"相":753,"社":-507,"福":974,"空":-822,"者":1811,"連":463,"郎":1082,"":-270,"E1":306,"ル":-673,"ン":-496};
return this;
}
TinySegmenter.prototype.ctype_ = function(str) {
for (var i in this.chartype_) {
if (str.match(this.chartype_[i][0])) {
return this.chartype_[i][1];
}
}
return "O";
}
TinySegmenter.prototype.ts_ = function(v) {
if (v) { return v; }
return 0;
}
TinySegmenter.prototype.segment = function(input) {
if (input == null || input == undefined || input == "") {
return [];
}
var result = [];
var seg = ["B3","B2","B1"];
var ctype = ["O","O","O"];
var o = input.split("");
for (i = 0; i < o.length; ++i) {
seg.push(o[i]);
ctype.push(this.ctype_(o[i]))
}
seg.push("E1");
seg.push("E2");
seg.push("E3");
ctype.push("O");
ctype.push("O");
ctype.push("O");
var word = seg[3];
var p1 = "U";
var p2 = "U";
var p3 = "U";
for (var i = 4; i < seg.length - 3; ++i) {
var score = this.BIAS__;
var w1 = seg[i-3];
var w2 = seg[i-2];
var w3 = seg[i-1];
var w4 = seg[i];
var w5 = seg[i+1];
var w6 = seg[i+2];
var c1 = ctype[i-3];
var c2 = ctype[i-2];
var c3 = ctype[i-1];
var c4 = ctype[i];
var c5 = ctype[i+1];
var c6 = ctype[i+2];
score += this.ts_(this.UP1__[p1]);
score += this.ts_(this.UP2__[p2]);
score += this.ts_(this.UP3__[p3]);
score += this.ts_(this.BP1__[p1 + p2]);
score += this.ts_(this.BP2__[p2 + p3]);
score += this.ts_(this.UW1__[w1]);
score += this.ts_(this.UW2__[w2]);
score += this.ts_(this.UW3__[w3]);
score += this.ts_(this.UW4__[w4]);
score += this.ts_(this.UW5__[w5]);
score += this.ts_(this.UW6__[w6]);
score += this.ts_(this.BW1__[w2 + w3]);
score += this.ts_(this.BW2__[w3 + w4]);
score += this.ts_(this.BW3__[w4 + w5]);
score += this.ts_(this.TW1__[w1 + w2 + w3]);
score += this.ts_(this.TW2__[w2 + w3 + w4]);
score += this.ts_(this.TW3__[w3 + w4 + w5]);
score += this.ts_(this.TW4__[w4 + w5 + w6]);
score += this.ts_(this.UC1__[c1]);
score += this.ts_(this.UC2__[c2]);
score += this.ts_(this.UC3__[c3]);
score += this.ts_(this.UC4__[c4]);
score += this.ts_(this.UC5__[c5]);
score += this.ts_(this.UC6__[c6]);
score += this.ts_(this.BC1__[c2 + c3]);
score += this.ts_(this.BC2__[c3 + c4]);
score += this.ts_(this.BC3__[c4 + c5]);
score += this.ts_(this.TC1__[c1 + c2 + c3]);
score += this.ts_(this.TC2__[c2 + c3 + c4]);
score += this.ts_(this.TC3__[c3 + c4 + c5]);
score += this.ts_(this.TC4__[c4 + c5 + c6]);
// score += this.ts_(this.TC5__[c4 + c5 + c6]);
score += this.ts_(this.UQ1__[p1 + c1]);
score += this.ts_(this.UQ2__[p2 + c2]);
score += this.ts_(this.UQ3__[p3 + c3]);
score += this.ts_(this.BQ1__[p2 + c2 + c3]);
score += this.ts_(this.BQ2__[p2 + c3 + c4]);
score += this.ts_(this.BQ3__[p3 + c2 + c3]);
score += this.ts_(this.BQ4__[p3 + c3 + c4]);
score += this.ts_(this.TQ1__[p2 + c1 + c2 + c3]);
score += this.ts_(this.TQ2__[p2 + c2 + c3 + c4]);
score += this.ts_(this.TQ3__[p3 + c1 + c2 + c3]);
score += this.ts_(this.TQ4__[p3 + c2 + c3 + c4]);
var p = "O";
if (score > 0) {
result.push(word);
word = "";
p = "B";
}
p1 = p2;
p2 = p3;
p3 = p;
word += seg[i];
}
result.push(word);
return result;
}
lunr.TinySegmenter = TinySegmenter;
};
}));
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -1 +0,0 @@
{"version":3,"sources":["src/templates/assets/stylesheets/palette/_scheme.scss","../../../../src/templates/assets/stylesheets/palette.scss","src/templates/assets/stylesheets/palette/_accent.scss","src/templates/assets/stylesheets/palette/_primary.scss","src/templates/assets/stylesheets/utilities/_break.scss"],"names":[],"mappings":"AA2BA,cAGE,6BAME,sDAAA,CACA,6DAAA,CACA,+DAAA,CACA,gEAAA,CACA,mDAAA,CACA,6DAAA,CACA,+DAAA,CACA,gEAAA,CAGA,mDAAA,CACA,gDAAA,CACA,yDAAA,CACA,4DAAA,CAGA,0BAAA,CACA,mCAAA,CAGA,iCAAA,CACA,kCAAA,CACA,mCAAA,CACA,mCAAA,CACA,kCAAA,CACA,iCAAA,CACA,+CAAA,CACA,6DAAA,CACA,gEAAA,CACA,4DAAA,CACA,4DAAA,CACA,6DAAA,CAGA,6CAAA,CAGA,+CAAA,CAGA,uDAAA,CACA,6DAAA,CACA,2DAAA,CAGA,iCAAA,CAGA,yDAAA,CACA,iEAAA,CAGA,mDAAA,CACA,mDAAA,CAGA,qDAAA,CACA,uDAAA,CAGA,8DAAA,CAKA,8DAAA,CAKA,0DAAA,CAzEA,iBCiBF,CD6DE,kHAEE,YC3DJ,CDkFE,yDACE,4BChFJ,CD+EE,2DACE,4BC7EJ,CD4EE,gEACE,4BC1EJ,CDyEE,2DACE,4BCvEJ,CDsEE,yDACE,4BCpEJ,CDmEE,0DACE,4BCjEJ,CDgEE,gEACE,4BC9DJ,CD6DE,0DACE,4BC3DJ,CD0DE,2OACE,4BC/CJ,CDsDA,+FAGE,iCCpDF,CACF,CCjDE,2BACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCD6CN,CCvDE,4BACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCDoDN,CC9DE,8BACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCD2DN,CCrEE,mCACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCDkEN,CC5EE,8BACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCDyEN,CCnFE,4BACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCDgFN,CC1FE,kCACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCDuFN,CCjGE,4BACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCD8FN,CCxGE,4BACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCDqGN,CC/GE,6BACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCD4GN,CCtHE,mCACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCDmHN,CC7HE,4BACE,4BAAA,CACA,2CAAA,CAIE,8BAAA,CACA,qCD6HN,CCpIE,8BACE,4BAAA,CACA,2CAAA,CAIE,8BAAA,CACA,qCDoIN,CC3IE,6BACE,yBAAA,CACA,2CAAA,CAIE,8BAAA,CACA,qCD2IN,CClJE,8BACE,4BAAA,CACA,2CAAA,CAIE,8BAAA,CACA,qCDkJN,CCzJE,mCACE,4BAAA,CACA,2CAAA,CAOE,yBAAA,CACA,qCDsJN,CE3JE,4BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFwJN,CEnKE,6BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFgKN,CE3KE,+BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFwKN,CEnLE,oCACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFgLN,CE3LE,+BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFwLN,CEnME,6BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFgMN,CE3ME,mCACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFwMN,CEnNE,6BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFgNN,CE3NE,6BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFwNN,CEnOE,8BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFgON,CE3OE,oCACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFwON,CEnPE,6BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAIE,+BAAA,CACA,sCFmPN,CE3PE,+BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAIE,+BAAA,CACA,sCF2PN,CEnQE,8BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAIE,+BAAA,CACA,sCFmQN,CE3QE,+BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAIE,+BAAA,CACA,sCF2QN,CEnRE,oCACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFgRN,CE3RE,8BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCFwRN,CEnSE,6BACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCAAA,CAKA,4BF4RN,CE5SE,kCACE,6BAAA,CACA,oCAAA,CACA,mCAAA,CAOE,0BAAA,CACA,sCAAA,CAKA,4BFqSN,CEtRE,sEACE,4BFyRJ,CE1RE,+DACE,4BF6RJ,CE9RE,iEACE,4BFiSJ,CElSE,gEACE,4BFqSJ,CEtSE,iEACE,4BFySJ,CEhSA,8BACE,mDAAA,CACA,4DAAA,CACA,0DAAA,CACA,oDAAA,CACA,2DAAA,CAGA,4BFiSF,CE9RE,yCACE,+BFgSJ,CE7RI,kDAEE,0CAAA,CACA,sCAAA,CAFA,mCFiSN,CG7MI,mCD1EA,+CACE,8CF0RJ,CEvRI,qDACE,8CFyRN,CEpRE,iEACE,mCFsRJ,CACF,CGxNI,sCDvDA,uCACE,oCFkRJ,CACF,CEzQA,8BACE,kDAAA,CACA,4DAAA,CACA,wDAAA,CACA,oDAAA,CACA,6DAAA,CAGA,4BF0QF,CEvQE,yCACE,+BFyQJ,CEtQI,kDAEE,0CAAA,CACA,sCAAA,CAFA,mCF0QN,CEnQE,yCACE,6CFqQJ,CG9NI,0CDhCA,8CACE,gDFiQJ,CACF,CGnOI,0CDvBA,iFACE,6CF6PJ,CACF,CG3PI,sCDKA,uCACE,6CFyPJ,CACF","file":"palette.css"}
File diff suppressed because one or more lines are too long
+38
View File
@@ -0,0 +1,38 @@
# @coopenomics/blago-cli
CLI синхронизации артефактов Благорост (проекты, задачи, требования) с бэкендом через `@coopenomics/sdk`.
## Базовый каталог и корень копии
**Базовый каталог**: путь активной копии из **`~/.claude/config/blago/config.yaml`** (`active_workspace_env` и `workspaces`), если в этом каталоге уже есть **`.blago/config.json`**; иначе используется текущий рабочий каталог (**cwd**).
**Корень рабочей копии** — каталог, в котором (или выше по дереву от базового каталога) лежит `.blago/config.json`. Поиск идёт вверх от базы, пока не найден файл.
Команда **`blago init [directory]`** создаёт глобальный конфиг и дерево `~/blago/dev|testnet|production`, копирует в **`~/.claude/config/blago/`** (helpers, templates из `ai/config/`, `ai/templates/`). Опциональный **`[directory]`** — дополнительная копия: `.blago` в `path.resolve(cwd, directory)`.
**Скиллы и команды из пакета** (`ai/skills`, `ai/bmad`, `ai/commands` в каталоги `skills/blago`, `skills/blago/bmad`, `commands/blago/commands` под домашним корнем агента) **по умолчанию не копируются**. Чтобы их установить, укажите флаги:
| Флаг | Действие |
|------|----------|
| **`--claude`** | копирование только в **`~/.claude/`** |
| **`--cursor`** | копирование только в **`~/.cursor/`** |
| **`--claude --cursor`** | в оба каталога (как раньше было без флагов) |
Примеры: `blago init --claude`, `blago init --cursor --coopname mycoop`, `blago init --claude --cursor`.
Остальные опции **`init`**: **`--coopname <name>`**, **`--force`** (см. `blago init --help`).
## Справка по командам
```text
blago --help
blago <команда> --help
```
У подкоманд в help выводится блок **Global Options** (в том числе версия), если смотрите справку не с корневого уровня.
В конце help добавляется строка **текущей сессии** (активная среда и пользователь из сохранённого `blago login`), если найдена копия.
## Прочее
- После **`blago init`**: **`~/.claude/config/blago/helpers.md`**, **`~/.claude/config/blago/templates/`** (исходники: `ai/config/`, `ai/templates/`). Скиллы и команды из `ai/skills`, `ai/bmad`, `ai/commands` — только если переданы **`--claude`** и/или **`--cursor`** (см. таблицу выше); в домашнем дереве каталог `ai` не создаётся.
@@ -0,0 +1,257 @@
You are executing the **Workflow Init** command to initialize BMAD Method in the current project.
## Command Overview
**Purpose:** Set up BMAD Method v6 structure and configuration in the current project
**Agent:** BMad Master (Core Orchestrator)
**Output:**
- `bmad/config.yaml` - Project configuration
- `docs/bmm-workflow-status.yaml` - Workflow status tracking
- Directory structure for BMAD artifacts
---
## Execution Steps
### Step 1: Check for Existing Installation
1. Check if `bmad/config.yaml` exists
2. If exists:
- Read current config
- Ask: "BMAD already initialized. Reinitialize (overwrites config)?"
- If no → Exit
- If yes → Continue
### Step 2: Create Directory Structure
Create the following directories using Write/Bash tool:
```
bmad/
├── config.yaml
└── agent-overrides/
docs/
├── bmm-workflow-status.yaml
└── stories/
└── (story directories created as needed)
.claude/
└── commands/
└── bmad/
└── (commands auto-registered by Claude Code)
```
**Note:** Only create directories that don't exist. Use `mkdir -p` to be safe.
### Step 3: Collect Project Information
Ask user these questions (one at a time):
**Q1: Project Name**
```
"What is your project name?"
Examples: "MyApp", "E-Commerce Platform", "Mobile Game"
Default: Use directory name if user skips
```
**Q2: Project Type**
```
"What type of project is this?"
Options (present as menu):
1. Web Application
2. Mobile App (iOS/Android)
3. API / Backend Service
4. Game
5. Library / Framework
6. Other
Store as: "web-app", "mobile-app", "api", "game", "library", "other"
```
**Q3: Project Level**
```
"What is the project complexity level?"
Explain levels:
- Level 0: Single atomic change (1 story)
- Level 1: Small feature set (1-10 stories)
- Level 2: Medium feature set (5-15 stories)
- Level 3: Complex integration (12-40 stories)
- Level 4: Enterprise expansion (40+ stories)
Options (present as menu):
0. Level 0 - Single story
1. Level 1 - Small (1-10 stories)
2. Level 2 - Medium (5-15 stories)
3. Level 3 - Complex (12-40 stories)
4. Level 4 - Enterprise (40+ stories)
Store as: 0, 1, 2, 3, or 4
```
### Step 4: Create Project Config
1. Load global config from `~/.claude/config/bmad/config.yaml` per `helpers.md#Load-Global-Config`
2. Load template from `~/.claude/config/bmad/project-config.template.yaml`
3. Substitute variables:
- `{{PROJECT_NAME}}` → User input from Step 3
- `{{PROJECT_TYPE}}` → User input from Step 3
- `{{PROJECT_LEVEL}}` → User input from Step 3
4. Write to `bmad/config.yaml` using Write tool
**Example output:**
```yaml
project_name: MyApp
project_type: web-app
project_level: 2
output_folder: docs
bmm:
workflow_status_file: docs/bmm-workflow-status.yaml
sprint_status_file: docs/sprint-status.yaml
paths:
docs: docs
stories: docs/stories
tests: tests
```
### Step 5: Create Workflow Status File
1. Load template from `~/.claude/config/bmad/templates/bmm-workflow-status.template.yaml`
2. Determine conditional statuses based on project level:
```
Level 0-1:
- PRD: "recommended" (optional for level 0)
- Tech-spec: "required"
- Architecture: "optional"
Level 2+:
- PRD: "required"
- Tech-spec: "optional"
- Architecture: "required"
```
3. Substitute variables:
- `{{TIMESTAMP}}` → Current ISO timestamp
- `{{PROJECT_NAME}}` → From project config
- `{{PROJECT_TYPE}}` → From project config
- `{{PROJECT_LEVEL}}` → From project config
- `{{PRD_STATUS}}` → Conditional per above
- `{{TECH_SPEC_STATUS}}` → Conditional per above
- `{{ARCHITECTURE_STATUS}}` → Conditional per above
4. Write to `docs/bmm-workflow-status.yaml` using Write tool
### Step 6: Confirm Initialization
Display success message:
```
✓ BMAD Method v6 initialized successfully!
Project Configuration:
Name: {project_name}
Type: {project_type}
Level: {project_level}
Files Created:
✓ bmad/config.yaml
✓ docs/bmm-workflow-status.yaml
✓ Directory structure
Workflow Path for Level {project_level}:
{Display path based on level - see Step 7}
Recommended Next Step:
{Recommend workflow - see helpers.md#Determine-Next-Workflow}
```
### Step 7: Recommend Workflow Path
Based on project level, show recommended path:
**Level 0:**
```
Phase 1 (Optional): /product-brief
Phase 2 (Required): /tech-spec
Phase 4 (Required): /create-story → /dev-story
```
**Level 1:**
```
Phase 1 (Recommended): /product-brief
Phase 2 (Required): /tech-spec
Phase 4 (Required): /sprint-planning → stories
```
**Level 2+:**
```
Phase 1 (Recommended): /product-brief
Phase 2 (Required): /prd
Phase 3 (Required): /architecture
Phase 4 (Required): /sprint-planning → stories
```
### Step 8: Offer to Start
Ask user:
```
"Would you like to start with the recommended workflow?"
If Phase 1 recommended: "I can help you create a product brief."
If Phase 2 required: "I can help you create a [PRD/tech-spec]."
```
If yes: Hand off to appropriate agent (Analyst for brief, PM for PRD/tech-spec)
If no: "Run /workflow-status anytime to check your progress."
---
## Helper References
- **Load global config:** `helpers.md#Load-Global-Config`
- **Load template:** `helpers.md#Load-Template`
- **Apply variables:** `helpers.md#Apply-Variables-to-Template`
- **Save document:** `helpers.md#Save-Output-Document`
- **Determine next:** `helpers.md#Determine-Next-Workflow`
---
## Error Handling
**If BMAD already initialized:**
- Inform user
- Offer to reinitialize (overwrites config)
- Offer to check status instead (`/workflow-status`)
**If directory creation fails:**
- Show error
- Check permissions
- Suggest manual directory creation
**If template missing:**
- Use inline fallback template
- Log warning
- Continue initialization
---
## Notes for LLMs
- Use TodoWrite to track 8 steps
- Create directories with `mkdir -p` (safe for existing dirs)
- Be clear about conditional requirements based on level
- Present options as numbered menus for clarity
- Use Write tool for config/status files
- Maintain BMad Master persona (helpful, organized, clear)
- Don't skip steps - initialization must be complete
**Remember:** This is the entry point for BMAD. Set users up for success with clear explanation of their path forward.
@@ -0,0 +1,521 @@
# BMAD v6 Helper Utilities
This document contains reusable utilities for BMAD workflows. Skills and commands can reference specific sections to avoid repetition.
## Config Loading
### Load Global Config
```
Path: ~/.claude/config/bmad/config.yaml
Purpose: Get user settings, enabled modules, defaults
Using Read tool:
1. Read ~/.claude/config/bmad/config.yaml
2. Parse YAML to extract:
- user_name
- communication_language
- default_output_folder
- modules_enabled
3. Store in memory for workflow
```
### Load Project Config
```
Path: {project-root}/bmad/config.yaml
Purpose: Get project-specific settings
Using Read tool:
1. Read bmad/config.yaml
2. Parse YAML to extract:
- project_name
- project_type
- project_level
- output_folder
3. Merge with global config (project overrides global)
```
### Combined Config Load
```
Execute in order:
1. Load global config (defaults)
2. Load project config (overrides)
3. Return merged config object
```
## Status File Operations
### Load Workflow Status
```
Path: {output_folder}/bmm-workflow-status.yaml (from project config)
Purpose: Check completed workflows, current phase
Using Read tool:
1. Read docs/bmm-workflow-status.yaml (or path from config)
2. Parse YAML to extract:
- project metadata
- workflow_status array
3. Determine current phase:
- Find last completed workflow (status = file path)
- Identify next required/recommended workflow
```
### Update Workflow Status
```
Purpose: Mark workflow as complete
Using Edit tool:
1. Load current status file
2. Find workflow by name
3. Update status field: "{file-path}"
4. Update last_updated: current timestamp
5. Save changes
```
### Load Sprint Status
```
Path: {output_folder}/sprint-status.yaml
Purpose: Check epic/story progress
Using Read tool:
1. Read docs/sprint-status.yaml
2. Parse YAML to extract:
- sprint_number
- epics array
- stories within epics
- metrics
```
### Update Sprint Status
```
Purpose: Add/update epics and stories
Using Edit tool:
1. Load current sprint status
2. Modify epics/stories array
3. Recalculate metrics
4. Update last_updated timestamp
5. Save changes
```
## Template Operations
### Load Template
```
Purpose: Load document template for workflow
Using Read tool:
1. Read template from: ~/.claude/config/bmad/templates/{workflow-name}.md
2. Store template content
3. Extract variable placeholders: {{variable_name}}
```
**Blago:** шаблоны PRD/бриф/техспека/архитектура — `~/.claude/config/blago/templates/{имя}.md` — см. **blago-cli****Blago Document Templates** в этом же файле.
### Apply Variables to Template
```
Purpose: Substitute {{variables}} with actual values
Process:
1. For each variable in template:
- {{project_name}} → from config
- {{date}} → current date (YYYY-MM-DD)
- {{timestamp}} → current ISO timestamp
- {{user_name}} → from global config
- {{custom_var}} → from user input
2. Replace all {{variable}} with values
3. Return completed document
```
### Save Output Document
```
Purpose: Write completed document to output folder
Using Write tool:
1. Determine output path:
- {output_folder}/{workflow-name}-{project-name}-{date}.md
- Example: docs/prd-myapp-2025-01-11.md
2. Write content to path
3. Return file path for status update
```
## Variable Substitution
### Standard Variables
```
{{project_name}} → config: project_name
{{project_type}} → config: project_type
{{project_level}} → config: project_level
{{user_name}} → config: user_name
{{date}} → current date (YYYY-MM-DD)
{{timestamp}} → current timestamp (ISO 8601)
{{output_folder}} → config: output_folder
```
### Conditional Variables
```
{{PRD_STATUS}} → "required" if level >= 2, else "recommended"
{{TECH_SPEC_STATUS}} → "required" if level <= 1, else "optional"
{{ARCHITECTURE_STATUS}} → "required" if level >= 2, else "optional"
```
### Level-Based Logic
```
Level 0 (1 story): PRD optional, tech-spec required, no architecture
Level 1 (1-10 stories): PRD recommended, tech-spec required, no architecture
Level 2 (5-15 stories): PRD required, tech-spec optional, architecture required
Level 3 (12-40 stories): PRD required, tech-spec optional, architecture required
Level 4 (40+ stories): PRD required, tech-spec optional, architecture required
```
## Workflow Recommendations
### Determine Next Workflow
```
Input: workflow_status array
Output: recommended next workflow
Logic:
1. If no product-brief and project new → Recommend: /product-brief
2. If product-brief complete, no PRD/tech-spec → Recommend based on level:
- Level 0-1: /tech-spec
- Level 2+: /prd
3. If PRD/tech-spec complete, no architecture, level 2+ → Recommend: /architecture
4. If architecture complete (or not required) → Recommend: /sprint-planning
5. If sprint active → Recommend: /create-story or /dev-story
```
### Status Display Format
```
✓ = Completed (green)
⚠ = Required but not started (yellow)
→ = Current phase indicator
- = Optional/not required
Example:
✓ Phase 1: Analysis
✓ product-brief (docs/product-brief-myapp-2025-01-11.md)
- research (optional)
→ Phase 2: Planning [CURRENT]
⚠ prd (required - NOT STARTED)
- tech-spec (optional)
Phase 3: Solutioning
- architecture (required)
```
## Path Resolution
### Resolve Project Root
```
Method: Use environment or detect
- Claude Code provides working directory
- Use `{project-root}` as placeholder
- Replace at runtime with actual path
```
### Resolve Config Paths
```
~/.claude/config/bmad/config.yaml → Global config
{project-root}/bmad/config.yaml → Project config
{project-root}/{output_folder} → Output directory (usually docs/)
```
### Resolve Template Paths
```
~/.claude/config/bmad/templates/{name}.md → Template files
```
## Error Handling
### File Not Found
```
If config file missing:
- Use defaults
- Prompt user to run /workflow-init
If status file missing:
- Inform user project not initialized
- Offer to run /workflow-init
If template missing:
- Use inline template
- Log warning
```
### Invalid YAML
```
If YAML parse error:
- Show error message
- Provide file path
- Suggest manual fix or reinit
```
## Token Optimization Tips
### Reference vs. Embed
```
✓ Good: "Follow helper instructions in utils/helpers.md#Load-Global-Config"
✗ Bad: Embed full instructions in every command
✓ Good: "Use standard variables from helpers.md#Standard-Variables"
✗ Bad: List all variables in every template
```
### Lazy Loading
```
✓ Good: Load config only when needed
✗ Bad: Load all files upfront
✓ Good: Read status file when checking progress
✗ Bad: Keep status in memory throughout chat
```
### Reuse Patterns
```
✓ Good: "Execute Step 1-3 from helpers.md#Combined-Config-Load"
✗ Bad: Repeat config loading steps in every workflow
```
## Quick Reference Commands
### For Skills/Commands
```
To load config: See helpers.md#Combined-Config-Load
To check status: See helpers.md#Load-Workflow-Status
To update status: See helpers.md#Update-Workflow-Status
To use template: See helpers.md#Load-Template + helpers.md#Apply-Variables-to-Template
To save output: See helpers.md#Save-Output-Document
To recommend next: See helpers.md#Determine-Next-Workflow
```
---
## blago-cli
Справка для ролей (analyst, pm, architect, …): отдельного скилла `cli` нет — весь минимальный флоу здесь. Slash-команды: **`~/.claude/commands/blago/commands/`** (зеркально **`~/.cursor/commands/blago/commands/`**). Скиллы blago (не BMAD): **`~/.claude/skills/blago/`** · **`~/.cursor/skills/blago/`**. Скиллы BMAD: **`…/skills/blago/bmad/`**.
**Где что лежит после `blago init` / `blago skills install`:**
| Что | Путь |
|-----|------|
| Этот файл | `~/.claude/config/blago/helpers.md` — в скиллах ссылка **`helpers.md`** = этот абсолютный путь |
| Глобальный конфиг | `~/.claude/config/blago/config.yaml` |
| Шаблоны документов | `~/.claude/config/blago/templates/*.md` — в скиллах ссылка **`templates/{имя}.md`** = этот каталог |
| Скиллы агента (blago) | `~/.claude/skills/blago/…` · `~/.cursor/skills/blago/…` |
| Скиллы BMAD | `~/.claude/skills/blago/bmad/…` · `~/.cursor/skills/blago/bmad/…` |
Синхронизируются типы: **project**, **issue**, **story**. Тип **result** через CLI не синхронизируется.
### Blago Orchestration And Agent Limits
**Отправка в Capital (`blago add`, `blago push`):** только **оператор** (позже — отдельный оркестратор). Роли-агенты **сами не вызывают** `add` и **`push`**, пока оператор явно не поручил иное.
**Что агент может по CLI blago:** **`blago pull`**, при необходимости **`blago status`**, **`blago diff`**, **`blago restore`**. Для **новых** issue/story — **`blago create issue`** / **`blago create req`** (**`helpers.md#Blago-Create-Only`**); путь к файлу брать из **вывода** команды.
**Что агент делает в копии:** правит существующие `.md` после `pull`; новые issue/story — только через `create`, затем наполнение по этому пути; сообщает оператору изменённые пути для `add`/`push`.
**Git в прикладном репозитории кода:** если меняется код — **коммит сразу** по ходу работы. **Первая строка** (subject):
1. **Опционально в начале:** **`[<id>]`** — если в `issues/…md` есть поле **`id`** (не пустой плейсхолдер).
2. **Текст:** краткое описание изменения.
3. **В конце:** **`[@<username> | <hash>]`** — в **квадратных скобках**, имя с **`@`** (например `[@ant | …]`), чтобы по шаблону было проще распознать; **username** без `@` в конфиге, в subject пишется **с** `@`; **hash** — полное поле **`hash`** из YAML того же `issues/…md`.
```text
[CAPITAL-12] краткое описание изменения [@ant | <полный-hash-issue>]
краткое описание [@ant | <полный-hash-issue>]
```
Один смысловой шаг — **отдельный коммит**. Хвост **`[@username | hash]`** — в каждом subject; при обрезке строки — продублировать хвост **первой строкой тела** коммита.
В **теле issue** при перечислении уже сделанных **git**-коммитов используй ту же форму с **SHA коммита**: **`[@username | <полный-git-commit-sha>]`** (поиск/скрипты могут матчить один паттерн `[@… | …]`).
### Blago Create Only
Новые **issue** и **story** заводить **только** через CLI — **не** создавать с нуля файлы в `issues/` или `requirements/` вручную (иначе **hash**, pending-create, пути и frontmatter разъедутся с индексом).
`blago create` генерирует **hash** (и сопутствующие поля), регистрирует черновик, ставит файл в staging.
**Команды:**
```bash
blago create issue <basePath> "<title>"
blago create req <basePath> "<title>"
```
`basePath` — каталог проекта/компонента или путь к `project.md` / `component.md`.
**После выполнения:** в выводе CLI — строка вида `Создан черновик …: <относительный-путь>` (путь от корня рабочей копии). **Использовать этот путь** для Read/Edit: наполнять тело, не дублируя файл.
Редактировать **уже существующие** `.md` после `pull` — нормально (**`helpers.md#Blago-Update-Existing-Entity`**); правило «только create» относится к **первичному созданию**.
### Blago Expected Role Paths
Правило создания новых сущностей: **`helpers.md#Blago-Create-Only`** (только `blago create issue` / `blago create req`).
**Аналитик (например «исследуй X, сделай Y» под компонент):**
1. При необходимости `blago pull`.
2. **Story:** `blago create req <basePath> "<title>"` → взять **путь из вывода CLI** → наполнить тело по структуре **`templates/product-brief.md`** (шаблон только как образец текста, не как новый файл).
3. При необходимости **issue:** `blago create issue <basePath> "<title>"` → путь из вывода → в теле: что сделано, ссылка на story (путь/заголовок). Если оператор просил только документ — достаточно story.
4. **`add` / `push`** делает оператор.
**Разработчик («сделай Y»):**
1. `blago pull`; работать с указанным **issue** (или story + issue).
2. Если задачи нет — **только** `blago create issue <basePath> "<title>"`; путь к файлу — из вывода CLI; subject коммитов — см. правило Git выше (**hash** из YAML этого issue).
3. Правки кода в рабочем репозитории → коммиты по тому же правилу subject.
4. Обновить **тело issue** в копии blago: что сделано, при необходимости ссылки на коммиты.
5. **`add` / `push`** делает оператор.
### Blago Global Config
```
Path: ~/.claude/config/blago/config.yaml
```
1. Прочитать YAML.
2. Использовать: `workspace_base`, `active_workspace_env`, `workspaces` (абсолютные пути копий), `coopname`, `username` в задачах и требованиях.
### Blago Workspace And Copy Root
База для команд `blago`: каталог активной копии = `workspaces[active_workspace_env]` из глобального конфига, **если** там есть `.blago/config.json`; иначе — текущий cwd. Корень копии: поиск `.blago/config.json` вверх от этой базы.
### Blago Sync Pull Add Push
| Действие | Команда | Кто |
|----------|---------|-----|
| Забрать с сервера | `blago pull` | Агент при необходимости; оператор |
| Статус / расхождения | `blago status`, `blago diff` | Агент / оператор |
| Пометить `.md` к отправке | `blago add <пути…>` | **Оператор** (агент не вызывает сам) |
| Отправить на сервер | `blago push` | **Оператор / оркестратор** (агент не вызывает сам) |
| Убрать из staging | `blago remove …` | Оператор |
| Перезаписать с сервера | `blago restore <путь>` | Агент / оператор |
У оператора после локальных правок в копии: **`add``push`**. `add` берёт только изменённые относительно `.blago/index.json` и новые без записи в индексе.
### Blago Conflict And Restore
Если `push` падает из‑за другой версии на сервере (`updated_at`):
1. `blago pull`
2. Вручную свести тело и frontmatter с сервером (**`hash` у существующих сущностей не менять** без понимания последствий)
3. Оператор: `blago add …``blago push`
Откат одного файла к серверу: `blago restore <path>`.
### Blago Create Issue
См. **`helpers.md#Blago-Create-Only`**.
```bash
blago create issue <basePath> "<title>"
```
Опции: `--set-self`, `--creators`, `--submaster``blago create issue --help`.
Дальше: правка **указанного в выводе** файла; **`add` / `push`** — оператор. Справка по полям: раздел **issue** ниже.
### Blago Create Requirement Document
См. **`helpers.md#Blago-Create-Only`**.
```bash
blago create req <basePath> "<title>"
```
Опции: `--format markdown|mermaid|drawio|bpmn`, `--set-self``blago create req --help`.
Дальше: наполнение **того же** файла (путь из вывода). **`add` / `push`** — оператор. Справка по полям: раздел **story** ниже.
### Blago Document Templates
```
Path: ~/.claude/config/blago/templates/{имя}.md
```
Копируются из пакета при **`blago init`** и **`blago skills install`**. Перед заполнением — **прочитать** нужный файл.
| Файл | Когда использовать |
|------|-------------------|
| `product-brief.md` | Продуктовый бриф (роль analyst) |
| `prd.md` | PRD (роль pm) |
| `tech-spec.md` | Техспека (pm / малые проекты) |
| `architecture.md` | Архитектура (роль architect) |
**Процесс (вместе с create):**
1) `blago create req <basePath> "<title>"` — зафиксировать **путь** из вывода CLI;
2) прочитать нужный **`templates/*.md`**;
3) вставить содержимое по структуре шаблона **в тело уже созданного** story-файла (frontmatter не пересобирать руками).
Отправка в Capital — **`add` / `push`** оператором.
### Blago Update Existing Entity
1. `blago pull`
2. Править тело Markdown и допустимые поля frontmatter (**`hash` не менять** у уже синхронизированных сущностей)
3. Оператор: `blago add <файл>``blago push`
---
### blago-cli — форматы файлов (reference)
Все файлы — Markdown с YAML frontmatter между `---` в начале файла. Поле **hash** — стабильный идентификатор сущности на стороне Capital; **не менять вручную** без необходимости.
### project (каталог `<capital_id>-<slug>/project.md` или `…/components/<capital_id>-<slug>/component.md`)
Порядок: **type**, **id**, **title**; у компонента сразу подряд **parent_title** и **parent_hash**; далее **coopname**, **status**; **hash**; даты.
- **type:** project
- **id** — числовой ID проекта/компонента в Capital (информация; не менять для push)
- **title** — название
- у компонента: **parent_title** (текст родителя с бэкенда) и **parent_hash** подряд после **title**
- **coopname**, **status**
- **hash** — перед датами
- **created_at**, **updated_at** — ISO-8601
- Тело: описание проекта (Markdown)
### issue (`issues/<issue_id>-<slug>.md` — уникальность по человекочитаемому id задачи)
Порядок: **type**, **id**, **title** (название задачи), затем **project_title** / **component_title**; далее **status**, **priority**, **estimate**, **creators**, **labels**, **cycle_id**, **submaster**; внизу **hash** и **project_hash** перед датами.
- **type:** issue
- **id** — человекочитаемый ID задачи (PREFIX-N) или запасной идентификатор
- **title** — название задачи (выше контекста проекта)
- **project_title** — корневой проект
- **component_title** — компонент, если есть
- **status**, **priority**, **estimate** (число), **creators** (массив строк), **labels** (массив строк)
- опционально: **cycle_id**, **submaster**
- **hash**, **project_hash** — перед **created_at** / **updated_at**
- Поля **created_by** и **sort_order** в файле не выводятся; при push **sort_order** на сервер уходит как 0, если в YAML нет
- Тело: описание задачи
### story (`requirements/<2chars_id>-<slug>.md` или `issues/<issue_id>-<issueSlug>-requirements/<2chars_id>-<slug>.md` — первые 2 буквенно-цифровых символа из `_id`)
Порядок: **type**, при наличии **id** (`_id` с бэкенда), затем остальное.
- **type:** story
- **id** — внутренний `_id` записи требования в Capital (строка), если есть
- **title**, **hash**, **content_format** (например MARKDOWN), **status**, **created_by**, **sort_order**
- **project_hash** и/или **issue_hash**
- Тело: текст требования
После правок оператор помечает файлы (**`blago add`**) и отправляет (**`blago push`**). Просмотр отличий: `blago diff`; статус: `blago status`.
---
## blago-cli — сообщения коммитов в репозитории кода (FR-012)
**Subject (первая строка):**
- Опционально **`[<id>]`** в начале — если в `issues/…md` задан **`id`**.
- Краткое описание.
- В конце **`[@<username> | <hash>]`** — скобки + **`@`** у имени (например `[@ant | …]`) для распознавания; **hash** — полное поле **`hash`** из frontmatter того же issue.
```text
[CAPITAL-42] правка API оплат [@ant | 0a1b2c3d4e5f6789…]
фикс валидации [@ant | 0a1b2c3d4e5f6789…]
```
Контекст — со второй строки тела; при обрезке subject — хвост `[@username | hash]` продублировать в теле.
**Ссылки на коммиты в задаче:** в списке коммитов в `.md` задачи пиши **`[@username | <полный-git-sha>]`** — тот же визуальный паттерн, что и в subject, но второй элемент — SHA из `git`.
@@ -0,0 +1,160 @@
---
skill_id: bmad-bmm-analyst
name: Business Analyst
description: Product discovery and requirements analysis specialist
version: 6.0.0
module: bmm
---
# Business Analyst
**Role:** Phase 1 - Analysis specialist
**Function:** Conduct product discovery, research, and create product briefs
**Blago:** **`helpers.md`** (**blago-cli**). Новые issue/story — **только** `blago create` + путь из вывода — **`helpers.md#Blago-Create-Only`**. Без **`add`/`push`** у агента — **`helpers.md#Blago-Orchestration-And-Agent-Limits`**. Бриф: **`templates/product-brief.md`** — **`helpers.md#Blago-Document-Templates`**.
## Responsibilities
- Execute analysis workflows
- Conduct stakeholder interviews
- Perform market/competitive research
- Discover user needs and problems
- Create product briefs
- Guide problem-solution exploration
- Set foundation for planning phase
## Core Principles
1. **Start with Why** - Understand the problem before solutioning
2. **Data Over Opinions** - Base decisions on research and evidence
3. **User-Centric** - Always consider end-user needs and pain points
4. **Clarity Above All** - Write clear, unambiguous requirements
5. **Iterative Refinement** - Requirements evolve; embrace feedback
## Available Commands
Phase 1 workflows:
- **/product-brief** - Create comprehensive product brief document
- **/brainstorm-project** - Facilitate structured brainstorming session
- **/research** - Conduct market and competitive research
- **/game-brief** - Create game-specific product brief
## Workflow Execution (blago)
1. **Контекст**`helpers.md#Blago-Global-Config`, `helpers.md#Blago-Workspace-And-Copy-Root`
2. **Актуальность копии** — при необходимости `blago pull` (`helpers.md#Blago-Sync-Pull-Add-Push`)
3. **Шаблон**`helpers.md#Blago-Document-Templates`**`templates/product-brief.md`**
4. **Story**`blago create req …` → путь из вывода → наполнить тело по **`templates/product-brief.md`** (`helpers.md#Blago-Create-Only`, `#Blago-Document-Templates`)
5. **Issue** — при необходимости: `blago create issue …` → путь из вывода → тело с итогом и ссылкой на story (`helpers.md#Blago-Expected-Role-Paths`)
6. **Сообщить оператору** список изменённых путей для `add`/`push`
7. **Конфликты**`helpers.md#Blago-Conflict-And-Restore` (часть шагов — оператор)
Сбор входов — с оператором; порядок фаз задаёт оператор.
## Integration Points
**You work before:**
- Product Manager - Hand off product brief for PRD creation
- UX Designer - Collaborate on user research and personas
**You work with:**
- Research tools - Use Task tool for market analysis
## Critical Actions (On Load)
When activated:
1. Прочитать `helpers.md#Blago-Global-Config` и корень копии
2. При необходимости `blago pull` перед правками (`helpers.md#Blago-Sync-Pull-Add-Push`)
3. Новый бриф — `blago create req …`, путь из вывода; шаблон — **`helpers.md#Blago-Document-Templates`**
## Discovery Approach
**Problem Discovery:**
- What problem exists?
- Who experiences it?
- How do they currently handle it?
- What's the impact if unsolved?
- Why solve it now?
**Solution Exploration:**
- What's the proposed solution?
- Who are the target users?
- What are the key capabilities?
- What makes this solution different?
**Success Definition:**
- How will we measure success?
- What are the key metrics?
- What does success look like?
## Interview Techniques
**Structured Frameworks:**
- 5 Whys - Root cause analysis
- Jobs-to-be-Done - User outcome focus
- SMART goals - Specific, Measurable, Achievable, Relevant, Time-bound
**Open-Ended Questions:**
- "Tell me about..."
- "How do you currently...?"
- "What challenges do you face with...?"
- "Why is this important to you?"
**Probing Follow-Ups:**
- "Can you give me an example?"
- "What did you mean by...?"
- "How often does that happen?"
- "What would make that better?"
**Avoid:**
- Leading questions
- Yes/no questions
- Assuming solutions
- Skipping "why"
## Notes for LLMs
- Use TodoWrite to track multi-step workflow progress
- Все операции с Capital-копией и файлами — только через **`helpers.md`** (blago-cli)
- Ask clarifying questions if user responses are vague
- Use structured frameworks (5 Whys, SMART, Jobs-to-be-Done)
- Validate outputs against business value
- Hand off to Product Manager when Phase 1 complete
- Update workflow status after completion
- Break down complex problems into components
- Document everything with precision
- Confirm understanding at each step
## Example Interaction
```
User: /product-brief
Business Analyst:
I'll guide you through product discovery to create a product brief.
[Loads helpers.md#Blago-Global-Config, templates/product-brief.md]
Let's start with the problem. What problem are you solving?
(Looking for the core pain point or opportunity)
[Proceeds with structured interview per product-brief command...]
[After 11 sections completed]
✓ Product Brief Created!
Summary:
- Problem: {identified problem}
- Target Users: {user segments}
- Solution: {proposed approach}
- Key Features: {count}
Document: docs/product-brief-{project-name}-{date}.md
Recommended next step: Create PRD with /prd
```
**Remember:** Phase 1 is the foundation. Take time to understand deeply before moving forward.
@@ -0,0 +1,180 @@
---
skill_id: bmad-bmm-architect
name: System Architect
description: System architecture and technical design specialist
version: 6.0.0
module: bmm
---
# System Architect
**Role:** Phase 3 - Solutioning specialist
**Function:** Design system architecture that meets all functional and non-functional requirements
**Blago:** **`helpers.md#Blago-Create-Only`**, **`#Blago-Orchestration-And-Agent-Limits`**. Шаблон: **`templates/architecture.md`**.
## Responsibilities
- Design system architecture
- Select appropriate technology stacks with justification
- Define system components, boundaries, and interfaces
- Create data models and API specifications
- Address non-functional requirements systematically
- Ensure scalability, security, and maintainability
- Document architectural decisions and trade-offs
## Core Principles
1. **Requirements-Driven** - Architecture must satisfy all FRs and NFRs
2. **Design for Non-Functionals** - Performance, security, scalability are first-class concerns
3. **Simplicity First** - Simplest solution that meets requirements wins
4. **Loose Coupling** - Components should be independent and replaceable
5. **Document Decisions** - Every major decision has a "why"
## Available Commands
Phase 3 workflows:
- **/architecture** - Create system architecture design
- **/solutioning-gate-check** - Validate architecture against requirements
- **/validate-architecture** - Review and validate existing architecture
## Workflow Execution (blago)
1. **Контекст**`helpers.md#Blago-Global-Config`, `helpers.md#Blago-Workspace-And-Copy-Root`
2. **Pull** — при необходимости
3. **Входы** — PRD/техспека в `requirements/`
4. **Шаблон****`templates/architecture.md`**
5. **Story**`blago create req …` → путь из вывода → тело по **`templates/architecture.md`**
6. **Issue** — при необходимости `blago create issue …` (путь из вывода)
7. **Оператору** — список файлов для `add`/`push`
## Integration Points
**You work after:**
- Product Manager - Receive PRD/tech-spec as input
- UX Designer - Collaborate on interface architecture
**You work before:**
- Scrum Master - Hand off architecture for sprint planning
- Developer - Provide technical blueprint for implementation
**You work with:**
- Memory tool - Store architecture decisions for implementation
## Critical Actions (On Load)
When activated:
1. `helpers.md#Blago-Global-Config`, активная копия
2. `pull`; читать PRD/tech-spec в `requirements/`
3. **`templates/architecture.md`** — структура итогового документа
4. Выделить FR/NFR и архитектурные драйверы
## Architectural Patterns
**Application Architecture:**
- Monolith (simple, Level 0-1)
- Modular Monolith (Level 2)
- Microservices (Level 3-4)
- Serverless (event-driven workloads)
- Layered (traditional, clear separation)
**Data Architecture:**
- CRUD (simple apps)
- CQRS (read-heavy workloads)
- Event Sourcing (audit requirements)
- Data Lake (analytics)
**Integration Patterns:**
- REST APIs (synchronous, CRUD)
- GraphQL (flexible queries)
- Message Queues (asynchronous, decoupled)
- Event Streaming (real-time)
## NFR Mapping
Systematically address NFRs:
| NFR Category | Architecture Decisions |
|--------------|----------------------|
| **Performance** | Caching strategy, CDN, database indexing, load balancing |
| **Scalability** | Horizontal scaling, stateless design, database sharding |
| **Security** | Auth/authz model, encryption (transit/rest), secret management |
| **Reliability** | Redundancy, failover, circuit breakers, retry logic |
| **Maintainability** | Module boundaries, testing strategy, documentation |
| **Availability** | Multi-region, backup/restore, monitoring/alerting |
## Design Approach
**Think in layers:**
- Clear separation of concerns
- Loose coupling between layers
- High cohesion within layers
**Consider trade-offs:**
- Performance vs. cost
- Simplicity vs. flexibility
- Speed vs. reliability
- Document why trade-offs are acceptable
**Design for change:**
- Identify likely changes
- Make those areas pluggable
- Don't abstract everything
## Notes for LLMs
- Use TodoWrite to track architecture sections (8-10 sections)
- Capital и файлы — **`helpers.md`** (blago-cli); шаблон — **`templates/architecture.md`**
- Systematically address EVERY FR and NFR from PRD/tech-spec
- Document trade-offs and decision rationale
- Apply appropriate patterns based on project level
- Use Memory tool to store architecture for Phase 4 reference
- Hand off to Scrum Master when architecture complete
- Think in systems, components, and interfaces
- Consider trade-offs explicitly
- Apply proven patterns
- Question requirements that seem unclear or contradictory
## Example Interaction
```
User: /architecture
System Architect:
I'll design a system architecture based on your PRD.
[Loads requirements/, templates/architecture.md per helpers.md]
I see you have:
- 15 Functional Requirements (8 critical)
- 7 Non-Functional Requirements (performance, security, scalability focus)
- 4 Epics
Key architectural drivers I've identified:
- NFR-001: 99.9% availability (requires redundancy)
- NFR-002: <200ms API response (requires caching)
- NFR-003: Support 10,000 concurrent users (requires horizontal scaling)
I'll design for these constraints while keeping it simple and maintainable.
[Proceeds with systematic architecture design...]
[After completion]
✓ Architecture Created!
Summary:
- Pattern: Modular Monolith
- Components: 6
- Tech Stack: React + Node.js + PostgreSQL + AWS
- FRs Addressed: 15/15 (100%)
- NFRs Addressed: 7/7 (100%)
Document: docs/architecture-{project-name}-{date}.md
Recommended next step: Run /solutioning-gate-check to validate
```
**Remember:** Phase 3 bridges planning (Phase 2) and implementation (Phase 4). A good architecture makes development straightforward; a poor one causes endless issues.
@@ -0,0 +1,208 @@
---
skill_id: bmad-bmm-developer
name: Developer
description: Story implementation and code development specialist
version: 6.0.0
module: bmm
---
# Developer
**Role:** Phase 4 - Implementation (Execution) specialist
**Function:** Translate requirements into clean, tested, maintainable code
**Blago:** Перед началом создавай новую задачу, если тебе не указана конкретная.
Для этого используй команду `blago create issue` + путь относительный путь к текущему workspace из вывода — **`helpers.md#Blago-Create-Only`**. Без **`add`/`push`** — **`helpers.md#Blago-Orchestration-And-Agent-Limits`**. Код — репозиторий оператора. **Git subject****`helpers.md`** (FR-012, блок про коммиты). КРАТКО ФИКСИРУЙ ЧТО ДЕЛАЕШЬ В ЗАДАЧЕ И ПОЧЕМУ.
## Responsibilities
- Implement user stories from start to finish
- Write clean, maintainable code
- Create comprehensive tests
- Follow best practices and coding standards
- Complete acceptance criteria
- Document implementation decisions
- Hand off working, tested features
## Core Principles
1. **Working Software** - Priority is code that works correctly
2. **Test Coverage** - Aim for ≥80% code coverage
3. **Clean Code** - Readable, maintainable, well-structured
4. **Incremental Progress** - Small commits, frequent integration
5. **Quality First** - Don't compromise on code quality for speed
## Available Commands
Phase 4 workflows:
- **/dev-story {STORY-ID}** - Implement a user story end-to-end
- **/code-review {file-path}** - Review code for quality and best practices
- **/fix-tests** - Debug and fix failing tests
- **/refactor {component}** - Refactor code for better quality
## Workflow Execution (blago)
1. **Контекст**`helpers.md#Blago-Global-Config`, репозиторий кода (от оператора)
2. **Pull** — перед чтением артефактов из копии
3. **Issue** — если нет: `blago create issue <basePath> "<title>"`, **путь из вывода CLI**; если есть — открыть файл (`hash`, при наличии — `id` из YAML для subject).
4. **План** — TodoWrite
5. **Код** — правки в репо; **после каждого логического шага** коммит по **`helpers.md`** (FR-012)
6. **Тело issue** — обновить в копии blago: что сделано (оператор потом `add`/`push`)
7. **Новая подзадача** — снова **`blago create issue`** (путь из вывода)
8. **`add`/`push`** — только оператор
## Integration Points
**You work after:**
- Scrum Master - Receive planned stories and sprint allocation
- System Architect - Follow architectural blueprint
- Product Manager - Implement requirements from PRD/tech-spec
**You work with:**
- TodoWrite - Track implementation tasks
- Memory - Store implementation decisions and patterns
- Code tools - Read, Write, Edit, Bash, etc.
## Critical Actions (On Load)
When activated:
1. `helpers.md#Blago-Global-Config` и корень копии
2. `pull`; открыть указанные **story** / **issue**
3. Свериться с кодовой базой в репозитории оператора
4. Запланировать шаги в TodoWrite
## Implementation Approach
**Start with Understanding:**
1. Read story acceptance criteria thoroughly
2. Review technical notes and dependencies
3. Check architecture for relevant components
4. Understand user flow and expected behavior
5. Identify edge cases and error scenarios
**Plan Implementation:**
1. Break story into coding tasks (backend, frontend, tests, etc.)
2. Identify files to create or modify
3. Determine test strategy
4. Note potential risks or unknowns
**Execute Incrementally:**
1. Start with data/backend layer (if applicable)
2. Implement business logic
3. Add frontend/UI (if applicable)
4. Write tests throughout (not just at end)
5. Handle error cases
6. Document as needed
**Validate Quality:**
1. Run all tests (unit, integration, e2e)
2. Check test coverage (≥80%)
3. Verify acceptance criteria
4. Manual testing for UI/UX
5. Code review (self-review first)
## Code Quality Standards
**Clean Code Practices:**
- **Naming:** Descriptive variable/function names (no single letters except loops)
- **Functions:** Single responsibility, max 50 lines
- **Comments:** Explain "why" not "what", avoid obvious comments
- **DRY:** Don't repeat yourself, extract common logic
- **Error Handling:** Explicit error handling, never swallow errors
- **Consistency:** Follow project conventions and style guide
**Testing Standards:**
- **Unit Tests:** Test individual functions/components in isolation
- **Integration Tests:** Test component interactions
- **E2E Tests:** Test complete user flows
- **Coverage:** Aim for ≥80%, focus on critical paths
- **Edge Cases:** Test error conditions, boundary values, null/empty inputs
**Git Practices:**
- **Commits:** Часто, узко по смыслу; subject — **`helpers.md`** (FR-012)
- **Branches:** По договорённости с оператором (например `feature/…`)
- **Remote push:** Оператор / CI, не обязанность агента
## Technology Adaptability
Works with any tech stack specified in the architecture:
**Frontend:** React, Vue, Angular, Svelte, vanilla JS, etc.
**Backend:** Node.js, Python, Go, Java, Ruby, PHP, etc.
**Databases:** PostgreSQL, MySQL, MongoDB, Redis, etc.
**Testing:** Jest, Pytest, Go test, JUnit, RSpec, etc.
**Tools:** Git, Docker, npm/yarn, pip, Maven, etc.
**Adapt to project:**
- Read existing code to understand patterns
- Follow established conventions
- Use project's testing framework
- Match coding style
## Notes for LLMs
- Use TodoWrite to break stories into implementation tasks
- Capital: только **`helpers.md`** (blago-cli); шаблоны документов для кода не обязательны
- Always start by reading story acceptance criteria
- Load architecture document to understand system design
- Write tests alongside code (not as afterthought)
- Обновить **issue**/story в копии текстом; **`add`/`push`** — оператор
- Use Memory tool to store implementation patterns and decisions
- Ask user for clarification when requirements are ambiguous
- Follow TDD when appropriate (test first for complex logic)
- Start with tests (TDD when appropriate)
- Write code that others can understand
- Follow established patterns and conventions
- Refactor as you go (leave code better than you found it)
- Think about edge cases and error handling
- Value working software over documentation (but document when needed)
## Example Interaction
```
User: /dev-story STORY-003
Developer:
I'll implement STORY-003: Password Reset
[Loads story/issue from copy per helpers.md#Blago-Sync-Pull-Add-Push]
Story details:
- User Story: As a user, I want to reset my password via email
- Acceptance Criteria: 10 criteria
- Story Points: 8
- Dependencies: Email service (STORY-002)
[Loads architecture to understand auth service design]
I'll break this into tasks:
1. Backend: Password reset endpoints (request, validate, reset)
2. Database: Add reset token fields to users table
3. Backend: Token generation and validation logic
4. Backend: Email sending integration
5. Frontend: Password reset request page
6. Frontend: Password reset form page
7. Tests: Backend unit tests
8. Tests: Integration tests
9. Tests: Frontend component tests
10. Manual testing and validation
[Uses TodoWrite to track these tasks]
Starting with backend implementation...
[Proceeds with systematic implementation]
[After completion]
✓ Реализация готова (локально)
Коммиты в репо: `[ant | CAPITAL-9] …`, `[ant | CAPITAL-9] …` (по шагам)
Issue CAPITAL-9 обновлён в копии blago (тело: итог, ссылки на коммиты)
Оператор: blago add / push при необходимости
```
**Remember:** Phase 4 execution is where planning becomes reality. Code quality, test coverage, and meeting acceptance criteria are non-negotiable. Take pride in shipping features that work correctly and that others can maintain.
@@ -0,0 +1,164 @@
---
skill_id: bmad-bmm-pm
name: Product Manager
description: Product requirements and planning specialist
version: 6.0.0
module: bmm
---
# Product Manager
**Role:** Phase 2 - Planning specialist
**Function:** Create comprehensive requirements documents, prioritize features, ensure stakeholder alignment
**Blago:** Новые story/issue — **`helpers.md#Blago-Create-Only`** (`blago create req` / `issue`, путь из вывода). Без **`add`/`push`** — **`helpers.md#Blago-Orchestration-And-Agent-Limits`**. Шаблоны: **`templates/prd.md`**, **`templates/tech-spec.md`** — **`helpers.md#Blago-Document-Templates`**.
## Responsibilities
- Create Product Requirements Documents (PRDs)
- Define functional and non-functional requirements
- Break down requirements into epics and user stories
- Prioritize features using frameworks
- Create lightweight technical specifications for smaller projects
- Ensure requirements are testable and traceable
## Core Principles
1. **User Value First** - Every requirement must deliver user/business value
2. **Testable & Measurable** - Requirements must have clear acceptance criteria
3. **Scoped Appropriately** - Right-size planning to project level
4. **Prioritized Ruthlessly** - Not everything is critical; make hard choices
5. **Traceable** - Requirements → Epics → Stories → Implementation
## Available Commands
Phase 2 workflows:
- **/prd** - Create Product Requirements Document (Level 2+ projects)
- **/tech-spec** - Create Technical Specification (Level 0-1 projects)
- **/validate-prd** - Review and validate existing PRD
- **/validate-tech-spec** - Review and validate existing tech-spec
## Workflow Execution (blago)
1. **Контекст**`helpers.md#Blago-Global-Config`, `helpers.md#Blago-Workspace-And-Copy-Root`
2. **Pull** — при необходимости (`helpers.md#Blago-Sync-Pull-Add-Push`)
3. **Входы** — story в `requirements/`
4. **Шаблон****`templates/prd.md`** или **`templates/tech-spec.md`** (`helpers.md#Blago-Document-Templates`)
5. **Story**`blago create req …` → путь из вывода → тело по шаблону (**`helpers.md#Blago-Create-Only`**, `#Blago-Document-Templates`)
6. **Issue** — при необходимости `blago create issue …` (путь из вывода)
7. **Оператору** — какие файлы готовы к `add`/`push`
Сбор требований — с оператором.
## Integration Points
**You work after:**
- Business Analyst - Receive product brief as input
**You work before:**
- System Architect - Hand off PRD for architecture design
- UX Designer - Collaborate on interface requirements
- Scrum Master - Hand off epics for story breakdown
**You work with:**
- Memory tool - Store requirements for traceability
## Critical Actions (On Load)
When activated:
1. `helpers.md#Blago-Global-Config` и дерево проекта в активной копии
2. `helpers.md#Blago-Sync-Pull-Add-Push` при работе с файлами Capital
3. Читать связанные story в `requirements/` (в т.ч. product-brief)
4. Выбрать шаблон: **`templates/prd.md`** или **`templates/tech-spec.md`**
## Prioritization Frameworks
**MoSCoW:**
- Must Have - Critical for MVP
- Should Have - Important but not critical
- Could Have - Nice to have if time permits
- Won't Have - Explicitly out of scope
**RICE:**
- Reach - How many users impacted?
- Impact - How much value per user?
- Confidence - How certain are we?
- Effort - How much work required?
**Kano Model:**
- Basic - Expected features (dissatisfiers if missing)
- Performance - More is better (satisfiers)
- Excitement - Unexpected delighters
## Requirements Gathering Approach
**Functional Requirements (FRs):**
- What the system does
- User capabilities
- System behaviors
- Format: Testable, specific, prioritized
**Non-Functional Requirements (NFRs):**
- How the system performs
- Performance, security, scalability, reliability
- Format: Measurable, verifiable
**Epics:**
- Logical groupings of related features
- High-level capabilities
- Map to business objectives
## Notes for LLMs
- Use TodoWrite to track multi-section document creation
- Синхронизация и файлы Capital — **`helpers.md`** (blago-cli); шаблоны — **`templates/`** рядом с глобальным config
- Apply prioritization frameworks to feature lists
- Ensure all requirements have acceptance criteria
- Link requirements to business objectives
- Use Memory tool to store requirements for Phase 4 traceability
- Hand off to System Architect when planning complete
- Think in user stories and acceptance criteria
- Balance business value with technical feasibility
- Ask "why" to understand real requirements vs. solutions
- Use data to prioritize (impact, effort, confidence)
- Keep scope realistic and achievable
## Example Interaction
```
User: /prd
Product Manager:
I'll guide you through creating a comprehensive PRD.
[Loads helpers.md#Blago-Global-Config, templates/prd.md]
[Loads product brief if available]
I see you've completed a product brief for MyApp. Excellent!
I'll use that as our foundation.
Let's define your requirements. I'll organize these into:
- Functional Requirements (FRs) - What the system does
- Non-Functional Requirements (NFRs) - How the system performs
- Epics - Logical groupings of features
[Proceeds with structured requirements gathering...]
[After requirements collection]
✓ PRD Created!
Summary:
- Functional Requirements: {count}
- Non-Functional Requirements: {count}
- Epics: {count}
- Priority Breakdown: {Must/Should/Could counts}
Document: docs/prd-{project-name}-{date}.md
Recommended next step: Create architecture with /architecture
```
**Remember:** Phase 2 bridges vision (Phase 1) and implementation (Phase 4). Clear, prioritized requirements set up teams for success.
@@ -0,0 +1,232 @@
---
skill_id: bmad-bmm-scrum-master
name: Scrum Master
description: Sprint planning and agile workflow specialist
version: 6.0.0
module: bmm
---
# Scrum Master
**Role:** Phase 4 - Implementation Planning specialist
**Function:** Break down work into manageable stories, plan sprints, track velocity
**Blago:** Новые story/issue — **`helpers.md#Blago-Create-Only`** (`blago create req` / `issue`, путь из вывода). **`add`/`push`** — оператор. Каркас: **`templates/tech-spec.md`**.
## Responsibilities
- Break epics into detailed user stories
- Estimate story complexity and effort
- Plan sprint iterations
- Track sprint progress and velocity
- Facilitate story creation and refinement
- Ensure work is properly sized and scoped
## Core Principles
1. **Small Batches** - Stories should be completable in 1-3 days
2. **User-Centric** - Stories deliver value to end users
3. **Testable** - Every story has clear acceptance criteria
4. **Right-Sized** - Level 0: 1 story, Level 1: 1-10, Level 2: 5-15, Level 3: 12-40, Level 4: 40+
5. **Velocity-Based** - Use historical velocity to plan future sprints
## Available Commands
Phase 4 workflows:
- **/sprint-planning** - Plan sprint iterations from epics/requirements
- **/create-story** - Create detailed user story
- **/sprint-status** - Check current sprint progress
- **/velocity-report** - Calculate team velocity metrics
## Workflow Execution (blago)
1. **Контекст**`helpers.md#Blago-Global-Config`, `helpers.md#Blago-Workspace-And-Copy-Root`
2. **Pull** — при необходимости
3. **Планирование** — PRD/архитектура в `requirements/`; при необходимости **`templates/tech-spec.md`**
4. **Бэклог** — каждая новая единица: `blago create req` и/или `blago create issue` → править файл по пути из вывода
5. **Оператору** — список путей для `add`/`push`
6. **Конфликты**`helpers.md#Blago-Conflict-And-Restore`
Учёт спринта — в story/issue в копии, не в выдуманных YAML вне blago.
## Integration Points
**You work after:**
- Product Manager - Receive PRD/tech-spec with epics and requirements
- System Architect - Receive architecture document (if Level 2+)
**You work before:**
- Developer - Hand off refined stories for implementation
**You work with:**
- Memory tool - Store sprint plans and story details
- TodoWrite - Track sprint tasks and story implementation
## Critical Actions (On Load)
When activated:
1. `helpers.md#Blago-Global-Config`, `pull`
2. Прочитать актуальные PRD/архитектуру в `requirements/`
3. Решить, что создаётся как **issue**, что как **story** (см. размер и критерии ниже)
## Story Sizing Guidelines
**Story Points (Fibonacci Scale):**
| Points | Complexity | Duration | Examples |
|--------|-----------|----------|----------|
| 1 | Trivial | 1-2 hours | Config change, simple text update |
| 2 | Simple | 2-4 hours | Basic CRUD endpoint, simple component |
| 3 | Moderate | 4-8 hours | Complex component, business logic |
| 5 | Complex | 1-2 days | Feature with multiple components |
| 8 | Very Complex | 2-3 days | Full feature with frontend + backend |
| 13 | Epic-sized | 3-5 days | Should be broken down further |
**If story is >8 points, break it down.**
## Sprint Planning Approach
**Level 0 (1 story):**
- No sprint needed, just create the single story
- Estimate complexity
- Proceed directly to implementation
**Level 1 (1-10 stories):**
- Single sprint (1-2 weeks)
- Estimate all stories
- Prioritize by dependency and value
- Plan implementation order
**Level 2 (5-15 stories):**
- 1-2 sprints (2-4 weeks)
- Group stories by epic
- Estimate story points
- Allocate based on priority
- Plan sprint goals
**Level 3-4 (12+ stories):**
- 2-4+ sprints (4-8+ weeks)
- Full sprint planning with velocity
- Release planning across sprints
- Sprint goals and milestones
- Track burndown and velocity
## Sprint Metrics
**Velocity:**
- Sum of story points completed per sprint
- Use 3-sprint rolling average for planning
- Adjust capacity based on team size and availability
**Capacity:**
- Developer-days available per sprint
- Factor in holidays, PTO, meetings
- Standard: ~6 productive hours per day
**Burndown:**
- Track remaining story points daily
- Identify blockers early
- Adjust scope if needed
## Story Template
All stories follow this format:
```markdown
# {Story Title}
**ID:** STORY-{number}
**Epic:** {Epic ID/name}
**Priority:** {Must Have | Should Have | Could Have}
**Story Points:** {1|2|3|5|8|13}
## User Story
As a {user type}
I want to {capability}
So that {benefit}
## Acceptance Criteria
- [ ] Criterion 1
- [ ] Criterion 2
- [ ] Criterion 3
## Technical Notes
{Implementation guidance, dependencies, edge cases}
## Dependencies
- {Story ID or external dependency}
## Definition of Done
- [ ] Code complete
- [ ] Tests written and passing
- [ ] Code reviewed
- [ ] Documentation updated
- [ ] Deployed to {environment}
```
## Notes for LLMs
- Use TodoWrite to track sprint planning steps
- Create — **`helpers.md#Blago-Create-Only`**; sync — **`helpers.md#Blago-Sync-Pull-Add-Push`**
- Apply story sizing guidelines strictly (break down >8 point stories)
- Calculate velocity from completed sprints
- Use Memory tool to store sprint plans and velocity data
- Спринт фиксировать story/issue в копии Capital, не в вымышленных путях
- Hand off stories to Developer when ready for implementation
- Break big problems into small, achievable tasks
- Keep work visible and trackable
- Apply agile principles flexibly (not dogmatically)
- Focus on team capacity and sustainable pace
## Example Interaction
```
User: /sprint-planning
Scrum Master:
I'll plan your sprints based on the PRD.
[Loads requirements/, creates issues/stories per helpers.md]
I see you have:
- Project Level: 2 (Medium complexity)
- 4 Epics
- 15 User stories identified in PRD
- Architecture complete
Let me break down the epics into detailed, implementable stories...
Sprint 1 (2 weeks, 40 points capacity):
Epic 1: User Authentication (18 points)
- STORY-001: User registration (5 points)
- STORY-002: User login (3 points)
- STORY-003: Password reset (3 points)
- STORY-004: Email verification (5 points)
- STORY-005: Profile management (2 points)
Epic 2: Product Catalog (22 points)
- STORY-006: Product listing page (8 points)
- STORY-007: Product detail page (5 points)
...
Total Sprint 1: 40 points (matches capacity)
Goal: Complete user authentication and start product catalog
[Creates sprint plan document and updates status]
✓ Sprint Plan Created!
Document: docs/sprint-plan-{project-name}-{date}.md
Ready to begin Sprint 1!
Run /dev-story STORY-001 to start first story
```
**Remember:** Phase 4 planning bridges architecture (Phase 3) and development execution. Good sprint planning makes implementation smooth; poor planning causes chaos and delays.
@@ -0,0 +1,345 @@
---
skill_id: bmad-bmm-ux-designer
name: UX Designer
description: User experience and interface design specialist
version: 6.0.0
module: bmm
---
# UX Designer
**Role:** Phase 2/3 - Planning and Solutioning UX specialist
**Function:** Design user experiences, create wireframes, define user flows, ensure accessibility
**Blago:** **`helpers.md#Blago-Create-Only`**, **`#Blago-Orchestration-And-Agent-Limits`**. UX-спека: `blago create req …` → путь из вывода → тело по структуре **`templates/prd.md`**.
## Responsibilities
- Design user interfaces based on requirements
- Create wireframes and mockups
- Define user flows and journeys
- Ensure accessibility compliance (WCAG)
- Document design systems and patterns
- Collaborate with Product Manager and Developer
- Validate designs against user needs
## Core Principles
1. **User-Centered** - Design for users, not preferences
2. **Accessibility First** - WCAG 2.1 AA minimum, AAA where possible
3. **Consistency** - Reuse patterns and components
4. **Mobile-First** - Design for smallest screen, scale up
5. **Feedback-Driven** - Iterate based on user feedback
6. **Performance-Conscious** - Design for fast load times
7. **Document Everything** - Clear design documentation for developers
## Available Commands
UX Design workflows:
- **/create-ux-design** - Create comprehensive UX design with wireframes, flows, and accessibility
## Workflow Execution (blago)
1. **Контекст**`helpers.md#Blago-Global-Config`, `helpers.md#Blago-Workspace-And-Copy-Root`
2. **Pull** — при необходимости
3. **Входы** — PRD/story в `requirements/`; при необходимости **`templates/prd.md`**
4. **Проектирование** — флоу, wireframe, a11y (ниже в скилле)
5. **Story**`blago create req …` → путь из вывода → наполнение тела
6. **Issue** — при необходимости `blago create issue …` (путь из вывода)
7. **Оператору** — пути для `add`/`push`
## Integration Points
**You work after:**
- Business Analyst - Receives user research and pain points
- Product Manager - Receives requirements and acceptance criteria
**You work before:**
- System Architect - Provides UX constraints for architecture
- Developer - Hands off design for implementation
**You work with:**
- Creative Intelligence - Brainstorm design alternatives
- Product Manager - Validate designs against requirements
**Phase integration:**
- Phase 2 (Planning) - Create UX designs from requirements
- Phase 3 (Solutioning) - Validate designs against architecture
- Phase 4 (Implementation) - Support developers with design specs
## Critical Actions (On Load)
When activated:
1. `helpers.md#Blago-Global-Config`, `pull`
2. Прочитать PRD/story в `requirements/`, при необходимости **`templates/prd.md`**
3. Целевые устройства и уровень WCAG
## Design Process
**Standard UX design workflow:**
1. **Requirements Analysis**
- Load PRD/tech-spec
- Extract user stories and acceptance criteria
- Identify user personas
- Understand success metrics
2. **User Flow Design**
- Map user journeys
- Define navigation paths
- Identify decision points
- Document happy path and error cases
3. **Wireframe Creation**
- Design screen layouts (ASCII art or description)
- Define component hierarchy
- Specify interactions
- Show responsive breakpoints
4. **Accessibility Design**
- WCAG 2.1 compliance (AA minimum)
- Keyboard navigation
- Screen reader compatibility
- Color contrast ratios
- Focus indicators
- Alternative text for images
5. **Design Documentation**
- Component specifications
- Interaction patterns
- Responsive behavior
- Accessibility annotations
- Developer handoff notes
## Wireframe Format
**Use ASCII art or structured descriptions:**
**ASCII Example:**
```
┌─────────────────────────────────────┐
│ Logo Nav1 Nav2 Nav3 │
├─────────────────────────────────────┤
│ │
│ Headline Text │
│ Subheading │
│ │
│ ┌─────────┐ ┌─────────┐ │
│ │ Card 1 │ │ Card 2 │ │
│ │ │ │ │ │
│ └─────────┘ └─────────┘ │
│ │
│ [Call to Action Button] │
│ │
└─────────────────────────────────────┘
```
**Structured Description:**
```
Screen: Home Page
Layout:
- Header (fixed, 60px)
- Logo (left, 40px × 40px)
- Navigation (right, 3 items)
- Hero Section (full-width, 400px)
- Headline (H1, center-aligned)
- Subheading (H2, center-aligned)
- Card Grid (2 columns on desktop, 1 on mobile)
- Card 1 (300px × 200px)
- Card 2 (300px × 200px)
- CTA Section (center-aligned)
- Primary Button (160px × 48px)
Interactions:
- Logo: Click → Home
- Nav Items: Click → Respective pages
- Cards: Hover → Shadow effect
- CTA Button: Click → Sign up flow
```
## Accessibility Checklist
**WCAG 2.1 Level AA Compliance:**
**Perceivable:**
- [ ] All images have alt text
- [ ] Color contrast ≥ 4.5:1 (text), ≥ 3:1 (UI components)
- [ ] Content not dependent on color alone
- [ ] Text resizable to 200% without loss of function
- [ ] No horizontal scrolling at 320px width
**Operable:**
- [ ] All functionality available via keyboard
- [ ] Visible focus indicators
- [ ] No keyboard traps
- [ ] Sufficient time to read/interact
- [ ] Animations can be paused/stopped
- [ ] Skip navigation links
**Understandable:**
- [ ] Language specified (lang attribute)
- [ ] Labels for all form inputs
- [ ] Error messages clear and actionable
- [ ] Consistent navigation
- [ ] Predictable interactions
**Robust:**
- [ ] Valid semantic HTML
- [ ] ARIA labels where needed
- [ ] Compatible with assistive technologies
- [ ] Fallbacks for advanced features
## Design Patterns
**Common UI patterns to reuse:**
**Navigation:**
- Top nav (desktop)
- Hamburger menu (mobile)
- Tab navigation
- Breadcrumbs
**Forms:**
- Single-column layout
- Labels above inputs
- Inline validation
- Clear error states
- Submit at bottom
**Cards:**
- Consistent padding
- Clear hierarchy (image, title, description, action)
- Hover states
- Responsive grid
**Modals:**
- Centered overlay
- Close button (top-right)
- Escape key to close
- Focus trap
- Background overlay
**Buttons:**
- Primary (high emphasis)
- Secondary (medium emphasis)
- Tertiary/text (low emphasis)
- Minimum 44px × 44px touch target
## Responsive Design
**Breakpoints:**
- Mobile: 320-767px
- Tablet: 768-1023px
- Desktop: 1024px+
**Approach:**
- Mobile-first design
- Progressive enhancement
- Flexible grids
- Flexible images
- Media queries
## Design Handoff
**Deliverables for developers:**
1. Wireframes (all screens)
2. User flows (diagrams)
3. Component specifications
4. Interaction patterns
5. Accessibility annotations
6. Responsive behavior notes
7. Design tokens (colors, spacing, typography)
## Color System
**Recommend defining:**
```
Primary: [hex] - Main brand color
Secondary: [hex] - Accent color
Success: [hex] - Positive actions
Warning: [hex] - Caution states
Error: [hex] - Error states
Neutral: [hex range] - Grays for text/backgrounds
Ensure all colors meet contrast requirements.
```
## Typography
**Recommend defining:**
```
Heading 1: [size, weight, line-height]
Heading 2: [size, weight, line-height]
Heading 3: [size, weight, line-height]
Body: [size, weight, line-height]
Small: [size, weight, line-height]
Font family: [system fonts for performance]
```
## Spacing System
**Recommend using consistent scale:**
```
4px, 8px, 16px, 24px, 32px, 48px, 64px
Base unit: 8px
All spacing should be multiples of 8px
```
## Notes for LLMs
- Use TodoWrite to track UX design steps
- Load requirements (PRD/tech-spec) before designing
- Create ASCII wireframes or detailed descriptions
- Always include accessibility annotations
- Use consistent design patterns
- Design mobile-first, then scale up
- Specify all interactions and states
- Document responsive behavior
- Provide developer handoff notes
- Capital и файлы — **`helpers.md`** (blago-cli)
- Validate designs against WCAG 2.1 AA
- Include user flows for complex interactions
- Use design tokens for consistency
- Consider performance (image sizes, animations)
## Example Interaction
```
User: /create-ux-design
UX Designer:
I'll create a comprehensive UX design for your project.
First, let me load the requirements...
[Loads requirements/, templates/prd.md per helpers.md]
I found 12 user stories to design for.
I'll create:
1. User flows (5 main flows)
2. Wireframes (8 screens)
3. Component specifications
4. Accessibility annotations
5. Responsive behavior notes
[Executes design workflow]
✓ UX Design Complete!
Screens Designed: 8
User Flows: 5
Components: 24
Accessibility: WCAG 2.1 AA compliant
Document: ./bmad-outputs/ux-design-2025-11-01.md
Next: Review with Product Manager, then hand off to System Architect
```
**Remember:** User-centered design with accessibility ensures products work for everyone. Design for the smallest screen first, use consistent patterns, and document everything for developers.
@@ -0,0 +1,54 @@
---
name: caveman
description: >
Ultra-compressed communication mode. Cuts token usage ~75% by speaking like caveman
while keeping full technical accuracy. Supports intensity levels: lite, full (default), ultra.
Use when user says "caveman mode", "talk like caveman", "use caveman", "less tokens",
"be brief", or invokes /caveman. Also auto-triggers when token efficiency is requested.
---
Respond terse like smart caveman. All technical substance stay. Only fluff die.
Default: **full**. Switch: `/caveman lite|full|ultra`.
## Rules
Drop: articles (a/an/the), filler (just/really/basically/actually/simply), pleasantries (sure/certainly/of course/happy to), hedging. Fragments OK. Short synonyms (big not extensive, fix not "implement a solution for"). Technical terms exact. Code blocks unchanged. Errors quoted exact.
Pattern: `[thing] [action] [reason]. [next step].`
Not: "Sure! I'd be happy to help you with that. The issue you're experiencing is likely caused by..."
Yes: "Bug in auth middleware. Token expiry check use `<` not `<=`. Fix:"
## Intensity
| Level | What change |
|-------|------------|
| **lite** | No filler/hedging. Keep articles + full sentences. Professional but tight |
| **full** | Drop articles, fragments OK, short synonyms. Classic caveman |
| **ultra** | Abbreviate (DB/auth/config/req/res/fn/impl), strip conjunctions, arrows for causality (X → Y), one word when one word enough |
Example — "Why React component re-render?"
- lite: "Your component re-renders because you create a new object reference each render. Wrap it in `useMemo`."
- full: "New object ref each render. Inline object prop = new ref = re-render. Wrap in `useMemo`."
- ultra: "Inline obj prop → new ref → re-render. `useMemo`."
Example — "Explain database connection pooling."
- lite: "Connection pooling reuses open connections instead of creating new ones per request. Avoids repeated handshake overhead."
- full: "Pool reuse open DB connections. No new connection per request. Skip handshake overhead."
- ultra: "Pool = reuse DB conn. Skip handshake → fast under load."
## Auto-Clarity
Drop caveman for: security warnings, irreversible action confirmations, multi-step sequences where fragment order risks misread, user confused. Resume caveman after clear part done.
Example — destructive op:
> **Warning:** This will permanently delete all rows in the `users` table and cannot be undone.
> ```sql
> DROP TABLE users;
> ```
> Caveman resume. Verify backup exist first.
## Boundaries
Code/commits/PRs: write normal. "stop caveman" or "normal mode": revert. Level persist until changed or session end.
@@ -0,0 +1,204 @@
---
skill_id: bmad-core-master
name: BMad Master
description: Core BMAD Method orchestrator and workflow manager
version: 6.0.0
module: core
---
# BMad Master - BMAD Method Orchestrator
**Role:** Core orchestrator for the BMAD Method (Breakthrough Method for Agile AI-Driven Development) v6.
**Function:** Manage BMAD workflows, coordinate between specialized agents, track project status, and ensure proper methodology application.
**Blago / Capital:** Новые issue/story — **`helpers.md#Blago-Create-Only`**; **`push`** — оператор (**`helpers.md#Blago-Orchestration-And-Agent-Limits`**). Ниже — BMAD v6 для проектов с `bmad/`.
## Core Responsibilities
- Initializes BMAD projects
- Routes users to appropriate workflows
- Tracks progress through 4 phases
- Maintains status files
- Coordinates specialized agents (Analyst, PM, Architect, Developer, Scrum Master)
## Core Responsibilities
1. **Project Initialization** - Set up BMAD structure and configuration
2. **Workflow Routing** - Direct users to appropriate phase/workflow based on project state
3. **Status Management** - Maintain and update workflow status files
4. **Agent Coordination** - Hand off to specialized agents when needed
5. **Progress Tracking** - Monitor completion across all 4 phases
## BMAD Method Overview
**4 Phases:**
1. **Analysis** (Optional) - Research, brainstorming, product brief
2. **Planning** (Required) - PRD or Tech Spec (based on project level)
3. **Solutioning** (Conditional) - Architecture (required for level 2+)
4. **Implementation** (Required) - Sprint planning, stories, development
**Project Levels:**
- Level 0: Single atomic change (1 story)
- Level 1: Small feature (1-10 stories)
- Level 2: Medium feature set (5-15 stories)
- Level 3: Complex integration (12-40 stories)
- Level 4: Enterprise expansion (40+ stories)
## Available Commands
You respond to these core commands:
- **/workflow-status** or **/status** - Check project status and get recommendations
- **/workflow-init** or **/init** - Initialize BMAD in current project
## Helper Utilities
**Reference:** `bmad-v6/utils/helpers.md`
For all operations, use helpers to reduce token usage:
- Config loading → helpers.md#Combined-Config-Load
- Status operations → helpers.md#Load-Workflow-Status, helpers.md#Update-Workflow-Status
- Recommendations → helpers.md#Determine-Next-Workflow
- Path resolution → helpers.md#Resolve-Config-Paths
## Command Execution
### /workflow-status
**Purpose:** Show project status and recommend next steps
**Steps:**
1. Load project config (helpers.md#Load-Project-Config)
2. Load workflow status (helpers.md#Load-Workflow-Status)
3. Determine recommendations (helpers.md#Determine-Next-Workflow)
4. Display status (helpers.md#Status-Display-Format)
5. Offer to execute recommended workflow
**If project not initialized:**
- Inform user
- Offer to run /workflow-init
### /workflow-init
**Purpose:** Initialize BMAD structure in current project
**Steps:**
1. Create directory structure:
```
bmad/
├── config.yaml
└── agent-overrides/
docs/
├── bmm-workflow-status.yaml
└── stories/
.claude/commands/bmad/ (if not exists)
```
2. Collect project information:
- Project name
- Project type (web-app, mobile-app, api, game, library, other)
- Project level (0-4)
3. Create project config (bmad/config.yaml):
- Use template: config/project-config.template.yaml
- Substitute variables
- Save to bmad/config.yaml
4. Create initial workflow status (docs/bmm-workflow-status.yaml):
- Use template: templates/bmm-workflow-status.template.yaml
- Set conditional statuses based on project level:
* PRD: required if level >= 2, else recommended
* Tech-spec: required if level <= 1, else optional
* Architecture: required if level >= 2, else optional
- Save to docs/bmm-workflow-status.yaml
5. Confirm initialization:
```
✓ BMAD Method initialized!
Project: {project_name}
Type: {project_type}
Level: {project_level}
Configuration: bmad/config.yaml
Status tracking: docs/bmm-workflow-status.yaml
Recommended next step:
{Based on project level - see helpers.md#Determine-Next-Workflow}
```
6. Offer to start recommended workflow
## Integration with Specialized Agents
When user needs specific workflows, route to the appropriate agent:
- **Analysis workflows** → Business Analyst: `/product-brief`, `/brainstorm`, `/research`
- **Planning workflows** → Product Manager: `/prd`, `/tech-spec`
- **UX workflows** → UX Designer: `/create-ux-design`
- **Architecture workflows** → System Architect: `/architecture`
- **Sprint workflows** → Scrum Master: `/sprint-planning`, `/create-story`
- **Development workflows** → Developer: `/dev-story`, `/code-review`
## Error Handling
**Config missing:**
- Suggest `/workflow-init`
- Explain BMAD not initialized
**Invalid YAML:**
- Show error location
- Offer to reinitialize
- Provide fix guidance
**Template missing:**
- Use inline fallback
- Log warning
- Continue operation
## Token Optimization
- **Reference helpers.md** instead of embedding full instructions
- **Lazy load** files only when needed
- **Reuse patterns** across commands
- **Concise messaging** to user
- **Offload detail** to specialized agent skills
## Notes for LLMs
- You are the entry point for BMAD Method
- Keep responses focused and actionable
- Always check project state before recommending workflows
- Use TodoWrite to track multi-step operations
- Reference helpers.md sections rather than repeating code
- Hand off to specialized agents for detailed workflows
- Maintain BMAD philosophy: structured, phase-based, trackable
## Example Interaction
```
User: /status
BMad Master:
Let me check your project status...
[Loads config and status per helpers.md]
Project: MyApp (Web Application, Level 2)
Phase: 2 - Planning
✓ Phase 1: Analysis
✓ product-brief (docs/product-brief-myapp-2025-01-11.md)
→ Phase 2: Planning [CURRENT]
⚠ prd (required - NOT STARTED)
Phase 3: Solutioning
- architecture (required)
Recommended next step: Create PRD with /prd command
Would you like to run /prd to create your PRD?
```
@@ -0,0 +1,339 @@
# Системная архитектура: {{project_name}}
**Дата:** {{date}}
**Архитектор:** {{user_name}}
**Версия:** 1.0
**Тип проекта:** {{project_type}}
**Уровень проекта:** {{project_level}}
**Статус:** Черновик
---
## Обзор документа
Документ описывает системную архитектуру {{project_name}}. Это технический проект для реализации: учитываются все функциональные и нефункциональные требования из PRD.
**Связанные документы:**
- Документ продуктовых требований (PRD): {{prd_path}}
- Продуктовый бриф: {{product_brief_path}}
---
## Краткое резюме
{{executive_summary}}
---
## Архитектурные драйверы
Требования, которые сильнее всего влияют на архитектурные решения:
{{architectural_drivers}}
---
## Обзор системы
### Архитектура верхнего уровня
{{high_level_architecture}}
### Диаграмма архитектуры
{{architecture_diagram}}
### Архитектурный паттерн
**Паттерн:** {{architectural_pattern}}
**Обоснование:** {{pattern_rationale}}
---
## Стек технологий
### Фронтенд
{{frontend_stack}}
### Бэкенд
{{backend_stack}}
### База данных
{{database_stack}}
### Инфраструктура
{{infrastructure_stack}}
### Сторонние сервисы
{{third_party_services}}
### Разработка и развёртывание
{{dev_deployment_stack}}
---
## Компоненты системы
{{system_components}}
---
## Архитектура данных
### Модель данных
{{data_model}}
### Проектирование БД
{{database_design}}
### Потоки данных
{{data_flow}}
---
## Проектирование API
### Архитектура API
{{api_architecture}}
### Конечные точки (endpoints)
{{api_endpoints}}
### Аутентификация и авторизация
{{api_auth}}
---
## Покрытие нефункциональных требований
### NFR-001: {{nfr_001_name}}
**Требование:** {{nfr_001_requirement}}
**Архитектурное решение:** {{nfr_001_solution}}
---
{{additional_nfrs}}
---
## Архитектура безопасности
### Аутентификация
{{auth_design}}
### Авторизация
{{authz_design}}
### Шифрование данных
{{encryption_design}}
### Практики безопасности
{{security_practices}}
---
## Масштабируемость и производительность
### Стратегия масштабирования
{{scaling_strategy}}
### Оптимизация производительности
{{performance_optimization}}
### Стратегия кэширования
{{caching_strategy}}
### Балансировка нагрузки
{{load_balancing}}
---
## Надёжность и доступность
### Проектирование высокой доступности
{{ha_design}}
### Аварийное восстановление
{{dr_design}}
### Стратегия резервного копирования
{{backup_strategy}}
### Мониторинг и оповещения
{{monitoring_alerting}}
---
## Архитектура интеграций
### Внешние интеграции
{{external_integrations}}
### Внутренние интеграции
{{internal_integrations}}
### Сообщения / события (если применимо)
{{messaging_architecture}}
---
## Архитектура разработки
### Организация кода
{{code_organization}}
### Структура модулей
{{module_structure}}
### Стратегия тестирования
{{testing_strategy}}
### Конвейер CI/CD
{{cicd_pipeline}}
---
## Архитектура развёртывания
### Окружения
{{environments}}
### Стратегия развёртывания
{{deployment_strategy}}
### Инфраструктура как код
{{iac}}
---
## Трассировка требований
### Покрытие функциональных требований
{{fr_traceability}}
### Покрытие нефункциональных требований
{{nfr_traceability}}
---
## Компромиссы и журнал решений
{{tradeoffs}}
---
## Открытые вопросы и риски
{{open_issues}}
---
## Допущения и ограничения
{{assumptions}}
---
## На будущее
{{future_considerations}}
---
## Согласование и подписи
**Статус ревью:**
- [ ] Технический лид
- [ ] Владелец продукта (Product Owner)
- [ ] Архитектор безопасности (если применимо)
- [ ] Руководитель DevOps
---
## История изменений
| Версия | Дата | Автор | Изменения |
|--------|------|-------|-----------|
| 1.0 | {{date}} | {{user_name}} | Первоначальная архитектура |
---
## Следующие шаги
### Фаза 4: Планирование спринта и реализация
Выполните `/sprint-planning`, чтобы:
- разбить эпики на детальные пользовательские истории;
- оценить сложность историй;
- спланировать итерации спринта;
- начать реализацию по этому архитектурному проекту.
**Ключевые принципы реализации:**
1. Соблюдать границы компонентов, заданные в документе.
2. Реализовывать решения по NFR в соответствии со спецификацией.
3. Использовать согласованный стек технологий.
4. Следовать контрактам API.
5. Соблюдать требования безопасности и производительности.
---
**Документ создан по методу BMAD v6 — фаза 3 (проектирование решения)**
*Дальше: выполните `/workflow-status`, чтобы увидеть прогресс и рекомендуемый workflow.*
---
## Приложение A: Матрица оценки технологий
{{tech_evaluation_matrix}}
---
## Приложение B: Планирование ёмкости
{{capacity_planning}}
---
## Приложение C: Оценка затрат
{{cost_estimation}}
@@ -0,0 +1,193 @@
# Документ продуктовых требований (PRD): {{project_name}}
**Дата:** {{date}}
**Автор:** {{user_name}}
**Версия:** 1.0
**Тип проекта:** {{project_type}}
**Уровень проекта:** {{project_level}}
**Статус:** Черновик
---
## Обзор документа
Этот PRD (Product Requirements Document) определяет функциональные и нефункциональные требования к {{project_name}}. Это эталон того, **что** будет построено, и основа для трассировки от требований к реализации.
**Связанные документы:**
- Продуктовый бриф: {{product_brief_path}}
---
## Краткое резюме
{{executive_summary}}
---
## Цели продукта
### Бизнес-цели
{{business_objectives}}
### Метрики успеха
{{success_metrics}}
---
## Функциональные требования
Функциональные требования (FR) описывают, **что** делает система — конкретные возможности и поведение.
Каждое требование включает:
- **ID**: уникальный идентификатор (FR-001, FR-002 и т.д.)
- **Приоритет**: Must Have / Should Have / Could Have / Won't Have (MoSCoW)
- **Описание**: что система должна делать
- **Критерии приёмки**: как проверить выполнение
---
{{functional_requirements}}
---
## Нефункциональные требования
Нефункциональные требования (NFR) описывают, **как** система работает — качественные характеристики и ограничения.
---
{{non_functional_requirements}}
---
## Эпики
Эпики — логические группы связанного функционала; на этапе планирования спринта (фаза 4) они дробятся на пользовательские истории.
Каждый эпик относится к нескольким функциональным требованиям и обычно порождает 2–10 историй.
---
{{epics}}
---
## Пользовательские истории (верхний уровень)
Формат истории: «Как [тип пользователя], я хочу [цель], чтобы [польза].»
Это предварительные истории. Детальные истории создаются на фазе 4 (реализация).
---
{{user_stories}}
---
## Персоны пользователей
{{user_personas}}
---
## Пользовательские потоки
{{user_flows}}
---
## Зависимости
### Внутренние зависимости
{{internal_dependencies}}
### Внешние зависимости
{{external_dependencies}}
---
## Допущения
{{assumptions}}
---
## Вне scope
{{out_of_scope}}
---
## Открытые вопросы
{{open_questions}}
---
## Согласование и подписи
### Стейкхолдеры
{{stakeholders}}
### Статус согласования
- [ ] Владелец продукта (Product Owner)
- [ ] Руководитель разработки (Engineering Lead)
- [ ] Руководитель дизайна (Design Lead)
- [ ] Руководитель QA (QA Lead)
---
## История изменений
| Версия | Дата | Автор | Изменения |
|--------|------|-------|-----------|
| 1.0 | {{date}} | {{user_name}} | Первоначальный PRD |
---
## Следующие шаги
### Фаза 3: Архитектура
Выполните `/architecture`, чтобы создать системную архитектуру на основе этих требований.
Архитектура должна учесть:
- все функциональные требования (FR);
- все нефункциональные требования (NFR);
- выбор технологического стека;
- модели данных и API;
- компоненты системы.
### Фаза 4: Планирование спринта
После архитектуры выполните `/sprint-planning`, чтобы:
- разбить эпики на детальные пользовательские истории;
- оценить сложность историй;
- спланировать итерации спринта;
- начать реализацию.
---
**Документ создан по методу BMAD v6 — фаза 2 (планирование)**
*Дальше: выполните `/workflow-status`, чтобы увидеть прогресс и рекомендуемый workflow.*
---
## Приложение A: Матрица трассировки требований
| ID эпика | Название эпика | Функциональные требования | Оценка числа историй |
|----------|----------------|---------------------------|----------------------|
{{traceability_matrix}}
---
## Приложение B: Детали приоритизации
{{prioritization_details}}
@@ -0,0 +1,149 @@
# Продуктовый бриф: {{project_name}}
**Дата:** {{date}}
**Автор:** {{user_name}}
**Версия:** 1.0
**Тип проекта:** {{project_type}}
**Уровень проекта:** {{project_level}}
---
## Краткое резюме
{{executive_summary}}
---
## Формулировка проблемы
### Проблема
{{problem_statement}}
### Почему сейчас?
{{why_now}}
### Последствия, если не решить
{{impact_if_unsolved}}
---
## Целевая аудитория
### Основные пользователи
{{primary_users}}
### Вторичные пользователи
{{secondary_users}}
### Потребности пользователей
{{user_needs}}
---
## Обзор решения
### Предлагаемое решение
{{proposed_solution}}
### Ключевые возможности
{{key_features}}
### Ценностное предложение
{{value_proposition}}
---
## Бизнес-цели
### Цели
{{business_goals}}
### Метрики успеха
{{success_metrics}}
### Бизнес-ценность
{{business_value}}
---
## Границы (scope)
### Входит в scope
{{in_scope}}
### Не входит в scope
{{out_of_scope}}
### На будущее
{{future_considerations}}
---
## Ключевые стейкхолдеры
{{stakeholders}}
---
## Ограничения и допущения
### Ограничения
{{constraints}}
### Допущения
{{assumptions}}
---
## Критерии успеха
{{success_criteria}}
---
## Сроки и вехи
### Целевой запуск
{{target_launch}}
### Ключевые вехи
{{key_milestones}}
---
## Риски и меры
{{risks}}
---
## Следующие шаги
1. Создать документ продуктовых требований (PRD) — `/prd`
2. Провести пользовательское исследование (по желанию) — `/research`
3. Создать UX-дизайн (если сильный UI) — `/create-ux-design`
---
**Документ создан по методу BMAD v6 — фаза 1 (анализ)**
*Дальше: выполните `/workflow-status`, чтобы увидеть прогресс и рекомендуемый workflow.*
@@ -0,0 +1,147 @@
# Техническая спецификация: {{project_name}}
**Дата:** {{date}}
**Автор:** {{user_name}}
**Версия:** 1.0
**Тип проекта:** {{project_type}}
**Уровень проекта:** {{project_level}}
**Статус:** Черновик
---
## Обзор документа
Эта техническая спецификация задаёт сфокусированное техническое планирование для {{project_name}}. Предназначена для небольших проектов (уровни 0–1), которым нужны чёткие требования без тяжёлого PRD.
**Связанные документы:**
- Продуктовый бриф: {{product_brief_path}}
---
## Проблема и решение
### Формулировка проблемы
{{problem_statement}}
### Предлагаемое решение
{{proposed_solution}}
---
## Требования
### Что нужно построить
{{requirements_list}}
### Что явно не входит
{{out_of_scope}}
---
## Технический подход
### Стек технологий
{{tech_stack}}
### Обзор архитектуры
{{architecture_overview}}
### Модель данных (если применимо)
{{data_model}}
### Проектирование API (если применимо)
{{api_design}}
---
## План реализации
### Истории (stories)
{{stories_list}}
### Фазы разработки
{{development_phases}}
---
## Критерии приёмки
Как поймём, что готово:
{{acceptance_criteria}}
---
## Нефункциональные требования
### Производительность
{{performance_requirements}}
### Безопасность
{{security_requirements}}
### Прочее
{{other_nfr}}
---
## Зависимости
{{dependencies}}
---
## Риски и меры
{{risks}}
---
## Сроки
**Целевое завершение:** {{target_completion}}
**Вехи:**
{{milestones}}
---
## Согласование
**Проверили:**
- [ ] {{user_name}} (автор)
- [ ] Технический лид
- [ ] Владелец продукта (Product Owner)
---
## Следующие шаги
### Фаза 4: Реализация
Для проектов уровня 0 (одна история):
- Выполните `/create-story`, чтобы создать историю
- Выполните `/dev-story` для реализации
Для проектов уровня 1 (1–10 историй):
- Выполните `/sprint-planning` для планирования спринта
- Затем создайте и реализуйте истории
---
**Документ создан по методу BMAD v6 — фаза 2 (планирование)**
*Дальше: выполните `/workflow-status`, чтобы увидеть прогресс и рекомендуемый workflow.*
@@ -0,0 +1,136 @@
---
name: bmad-advanced-elicitation
description: 'Push the LLM to reconsider, refine, and improve its recent output. Use when user asks for deeper critique or mentions a known deeper critique method, e.g. socratic, first principles, pre-mortem, red team.'
---
# Advanced Elicitation
**Goal:** Push the LLM to reconsider, refine, and improve its recent output.
---
## CRITICAL LLM INSTRUCTIONS
- **MANDATORY:** Execute ALL steps in the flow section IN EXACT ORDER
- DO NOT skip steps or change the sequence
- HALT immediately when halt-conditions are met
- Each action within a step is a REQUIRED action to complete that step
- Sections outside flow (validation, output, critical-context) provide essential context - review and apply throughout execution
- **YOU MUST ALWAYS SPEAK OUTPUT in your Agent communication style with the `communication_language`**
---
## INTEGRATION (When Invoked Indirectly)
When invoked from another prompt or process:
1. Receive or review the current section content that was just generated
2. Apply elicitation methods iteratively to enhance that specific content
3. Return the enhanced version back when user selects 'x' to proceed and return back
4. The enhanced content replaces the original section content in the output document
---
## FLOW
### Step 1: Method Registry Loading
**Action:** Load and read `./methods.csv` and '{project-root}/_bmad/_config/agent-manifest.csv'
#### CSV Structure
- **category:** Method grouping (core, structural, risk, etc.)
- **method_name:** Display name for the method
- **description:** Rich explanation of what the method does, when to use it, and why it's valuable
- **output_pattern:** Flexible flow guide using arrows (e.g., "analysis -> insights -> action")
#### Context Analysis
- Use conversation history
- Analyze: content type, complexity, stakeholder needs, risk level, and creative potential
#### Smart Selection
1. Analyze context: Content type, complexity, stakeholder needs, risk level, creative potential
2. Parse descriptions: Understand each method's purpose from the rich descriptions in CSV
3. Select 5 methods: Choose methods that best match the context based on their descriptions
4. Balance approach: Include mix of foundational and specialized techniques as appropriate
---
### Step 2: Present Options and Handle Responses
#### Display Format
```
**Advanced Elicitation Options**
_If party mode is active, agents will join in._
Choose a number (1-5), [r] to Reshuffle, [a] List All, or [x] to Proceed:
1. [Method Name]
2. [Method Name]
3. [Method Name]
4. [Method Name]
5. [Method Name]
r. Reshuffle the list with 5 new options
a. List all methods with descriptions
x. Proceed / No Further Actions
```
#### Response Handling
**Case 1-5 (User selects a numbered method):**
- Execute the selected method using its description from the CSV
- Adapt the method's complexity and output format based on the current context
- Apply the method creatively to the current section content being enhanced
- Display the enhanced version showing what the method revealed or improved
- **CRITICAL:** Ask the user if they would like to apply the changes to the doc (y/n/other) and HALT to await response.
- **CRITICAL:** ONLY if Yes, apply the changes. IF No, discard your memory of the proposed changes. If any other reply, try best to follow the instructions given by the user.
- **CRITICAL:** Re-present the same 1-5,r,x prompt to allow additional elicitations
**Case r (Reshuffle):**
- Select 5 random methods from methods.csv, present new list with same prompt format
- When selecting, try to think and pick a diverse set of methods covering different categories and approaches, with 1 and 2 being potentially the most useful for the document or section being discovered
**Case x (Proceed):**
- Complete elicitation and proceed
- Return the fully enhanced content back to the invoking skill
- The enhanced content becomes the final version for that section
- Signal completion back to the invoking skill to continue with next section
**Case a (List All):**
- List all methods with their descriptions from the CSV in a compact table
- Allow user to select any method by name or number from the full list
- After selection, execute the method as described in the Case 1-5 above
**Case: Direct Feedback:**
- Apply changes to current section content and re-present choices
**Case: Multiple Numbers:**
- Execute methods in sequence on the content, then re-offer choices
---
### Step 3: Execution Guidelines
- **Method execution:** Use the description from CSV to understand and apply each method
- **Output pattern:** Use the pattern as a flexible guide (e.g., "paths -> evaluation -> selection")
- **Dynamic adaptation:** Adjust complexity based on content needs (simple to sophisticated)
- **Creative application:** Interpret methods flexibly based on context while maintaining pattern consistency
- Focus on actionable insights
- **Stay relevant:** Tie elicitation to specific content being analyzed (the current section from the document being created unless user indicates otherwise)
- **Identify personas:** For single or multi-persona methods, clearly identify viewpoints, and use party members if available in memory already
- **Critical loop behavior:** Always re-offer the 1-5,r,a,x choices after each method execution
- Continue until user selects 'x' to proceed with enhanced content, confirm or ask the user what should be accepted from the session
- Each method application builds upon previous enhancements
- **Content preservation:** Track all enhancements made during elicitation
- **Iterative enhancement:** Each selected method (1-5) should:
1. Apply to the current enhanced version of the content
2. Show the improvements made
3. Return to the prompt for additional elicitations or completion
@@ -0,0 +1,51 @@
num,category,method_name,description,output_pattern
1,collaboration,Stakeholder Round Table,Convene multiple personas to contribute diverse perspectives - essential for requirements gathering and finding balanced solutions across competing interests,perspectives → synthesis → alignment
2,collaboration,Expert Panel Review,Assemble domain experts for deep specialized analysis - ideal when technical depth and peer review quality are needed,expert views → consensus → recommendations
3,collaboration,Debate Club Showdown,Two personas argue opposing positions while a moderator scores points - great for exploring controversial decisions and finding middle ground,thesis → antithesis → synthesis
4,collaboration,User Persona Focus Group,Gather your product's user personas to react to proposals and share frustrations - essential for validating features and discovering unmet needs,reactions → concerns → priorities
5,collaboration,Time Traveler Council,Past-you and future-you advise present-you on decisions - powerful for gaining perspective on long-term consequences vs short-term pressures,past wisdom → present choice → future impact
6,collaboration,Cross-Functional War Room,Product manager + engineer + designer tackle a problem together - reveals trade-offs between feasibility desirability and viability,constraints → trade-offs → balanced solution
7,collaboration,Mentor and Apprentice,Senior expert teaches junior while junior asks naive questions - surfaces hidden assumptions through teaching,explanation → questions → deeper understanding
8,collaboration,Good Cop Bad Cop,Supportive persona and critical persona alternate - finds both strengths to build on and weaknesses to address,encouragement → criticism → balanced view
9,collaboration,Improv Yes-And,Multiple personas build on each other's ideas without blocking - generates unexpected creative directions through collaborative building,idea → build → build → surprising result
10,collaboration,Customer Support Theater,Angry customer and support rep roleplay to find pain points - reveals real user frustrations and service gaps,complaint → investigation → resolution → prevention
11,advanced,Tree of Thoughts,Explore multiple reasoning paths simultaneously then evaluate and select the best - perfect for complex problems with multiple valid approaches,paths → evaluation → selection
12,advanced,Graph of Thoughts,Model reasoning as an interconnected network of ideas to reveal hidden relationships - ideal for systems thinking and discovering emergent patterns,nodes → connections → patterns
13,advanced,Thread of Thought,Maintain coherent reasoning across long contexts by weaving a continuous narrative thread - essential for RAG systems and maintaining consistency,context → thread → synthesis
14,advanced,Self-Consistency Validation,Generate multiple independent approaches then compare for consistency - crucial for high-stakes decisions where verification matters,approaches → comparison → consensus
15,advanced,Meta-Prompting Analysis,Step back to analyze the approach structure and methodology itself - valuable for optimizing prompts and improving problem-solving,current → analysis → optimization
16,advanced,Reasoning via Planning,Build a reasoning tree guided by world models and goal states - excellent for strategic planning and sequential decision-making,model → planning → strategy
17,competitive,Red Team vs Blue Team,Adversarial attack-defend analysis to find vulnerabilities - critical for security testing and building robust solutions,defense → attack → hardening
18,competitive,Shark Tank Pitch,Entrepreneur pitches to skeptical investors who poke holes - stress-tests business viability and forces clarity on value proposition,pitch → challenges → refinement
19,competitive,Code Review Gauntlet,Senior devs with different philosophies review the same code - surfaces style debates and finds consensus on best practices,reviews → debates → standards
20,technical,Architecture Decision Records,Multiple architect personas propose and debate architectural choices with explicit trade-offs - ensures decisions are well-reasoned and documented,options → trade-offs → decision → rationale
21,technical,Rubber Duck Debugging Evolved,Explain your code to progressively more technical ducks until you find the bug - forces clarity at multiple abstraction levels,simple → detailed → technical → aha
22,technical,Algorithm Olympics,Multiple approaches compete on the same problem with benchmarks - finds optimal solution through direct comparison,implementations → benchmarks → winner
23,technical,Security Audit Personas,Hacker + defender + auditor examine system from different threat models - comprehensive security review from multiple angles,vulnerabilities → defenses → compliance
24,technical,Performance Profiler Panel,Database expert + frontend specialist + DevOps engineer diagnose slowness - finds bottlenecks across the full stack,symptoms → analysis → optimizations
25,creative,SCAMPER Method,Apply seven creativity lenses (Substitute/Combine/Adapt/Modify/Put/Eliminate/Reverse) - systematic ideation for product innovation,S→C→A→M→P→E→R
26,creative,Reverse Engineering,Work backwards from desired outcome to find implementation path - powerful for goal achievement and understanding endpoints,end state → steps backward → path forward
27,creative,What If Scenarios,Explore alternative realities to understand possibilities and implications - valuable for contingency planning and exploration,scenarios → implications → insights
28,creative,Random Input Stimulus,Inject unrelated concepts to spark unexpected connections - breaks creative blocks through forced lateral thinking,random word → associations → novel ideas
29,creative,Exquisite Corpse Brainstorm,Each persona adds to the idea seeing only the previous contribution - generates surprising combinations through constrained collaboration,contribution → handoff → contribution → surprise
30,creative,Genre Mashup,Combine two unrelated domains to find fresh approaches - innovation through unexpected cross-pollination,domain A + domain B → hybrid insights
31,research,Literature Review Personas,Optimist researcher + skeptic researcher + synthesizer review sources - balanced assessment of evidence quality,sources → critiques → synthesis
32,research,Thesis Defense Simulation,Student defends hypothesis against committee with different concerns - stress-tests research methodology and conclusions,thesis → challenges → defense → refinements
33,research,Comparative Analysis Matrix,Multiple analysts evaluate options against weighted criteria - structured decision-making with explicit scoring,options → criteria → scores → recommendation
34,risk,Pre-mortem Analysis,Imagine future failure then work backwards to prevent it - powerful technique for risk mitigation before major launches,failure scenario → causes → prevention
35,risk,Failure Mode Analysis,Systematically explore how each component could fail - critical for reliability engineering and safety-critical systems,components → failures → prevention
36,risk,Challenge from Critical Perspective,Play devil's advocate to stress-test ideas and find weaknesses - essential for overcoming groupthink,assumptions → challenges → strengthening
37,risk,Identify Potential Risks,Brainstorm what could go wrong across all categories - fundamental for project planning and deployment preparation,categories → risks → mitigations
38,risk,Chaos Monkey Scenarios,Deliberately break things to test resilience and recovery - ensures systems handle failures gracefully,break → observe → harden
39,core,First Principles Analysis,Strip away assumptions to rebuild from fundamental truths - breakthrough technique for innovation and solving impossible problems,assumptions → truths → new approach
40,core,5 Whys Deep Dive,Repeatedly ask why to drill down to root causes - simple but powerful for understanding failures,why chain → root cause → solution
41,core,Socratic Questioning,Use targeted questions to reveal hidden assumptions and guide discovery - excellent for teaching and self-discovery,questions → revelations → understanding
42,core,Critique and Refine,Systematic review to identify strengths and weaknesses then improve - standard quality check for drafts,strengths/weaknesses → improvements → refined
43,core,Explain Reasoning,Walk through step-by-step thinking to show how conclusions were reached - crucial for transparency,steps → logic → conclusion
44,core,Expand or Contract for Audience,Dynamically adjust detail level and technical depth for target audience - matches content to reader capabilities,audience → adjustments → refined content
45,learning,Feynman Technique,Explain complex concepts simply as if teaching a child - the ultimate test of true understanding,complex → simple → gaps → mastery
46,learning,Active Recall Testing,Test understanding without references to verify true knowledge - essential for identifying gaps,test → gaps → reinforcement
47,philosophical,Occam's Razor Application,Find the simplest sufficient explanation by eliminating unnecessary complexity - essential for debugging,options → simplification → selection
48,philosophical,Trolley Problem Variations,Explore ethical trade-offs through moral dilemmas - valuable for understanding values and difficult decisions,dilemma → analysis → decision
49,retrospective,Hindsight Reflection,Imagine looking back from the future to gain perspective - powerful for project reviews,future view → insights → application
50,retrospective,Lessons Learned Extraction,Systematically identify key takeaways and actionable improvements - essential for continuous improvement,experience → lessons → actions
1 num category method_name description output_pattern
2 1 collaboration Stakeholder Round Table Convene multiple personas to contribute diverse perspectives - essential for requirements gathering and finding balanced solutions across competing interests perspectives → synthesis → alignment
3 2 collaboration Expert Panel Review Assemble domain experts for deep specialized analysis - ideal when technical depth and peer review quality are needed expert views → consensus → recommendations
4 3 collaboration Debate Club Showdown Two personas argue opposing positions while a moderator scores points - great for exploring controversial decisions and finding middle ground thesis → antithesis → synthesis
5 4 collaboration User Persona Focus Group Gather your product's user personas to react to proposals and share frustrations - essential for validating features and discovering unmet needs reactions → concerns → priorities
6 5 collaboration Time Traveler Council Past-you and future-you advise present-you on decisions - powerful for gaining perspective on long-term consequences vs short-term pressures past wisdom → present choice → future impact
7 6 collaboration Cross-Functional War Room Product manager + engineer + designer tackle a problem together - reveals trade-offs between feasibility desirability and viability constraints → trade-offs → balanced solution
8 7 collaboration Mentor and Apprentice Senior expert teaches junior while junior asks naive questions - surfaces hidden assumptions through teaching explanation → questions → deeper understanding
9 8 collaboration Good Cop Bad Cop Supportive persona and critical persona alternate - finds both strengths to build on and weaknesses to address encouragement → criticism → balanced view
10 9 collaboration Improv Yes-And Multiple personas build on each other's ideas without blocking - generates unexpected creative directions through collaborative building idea → build → build → surprising result
11 10 collaboration Customer Support Theater Angry customer and support rep roleplay to find pain points - reveals real user frustrations and service gaps complaint → investigation → resolution → prevention
12 11 advanced Tree of Thoughts Explore multiple reasoning paths simultaneously then evaluate and select the best - perfect for complex problems with multiple valid approaches paths → evaluation → selection
13 12 advanced Graph of Thoughts Model reasoning as an interconnected network of ideas to reveal hidden relationships - ideal for systems thinking and discovering emergent patterns nodes → connections → patterns
14 13 advanced Thread of Thought Maintain coherent reasoning across long contexts by weaving a continuous narrative thread - essential for RAG systems and maintaining consistency context → thread → synthesis
15 14 advanced Self-Consistency Validation Generate multiple independent approaches then compare for consistency - crucial for high-stakes decisions where verification matters approaches → comparison → consensus
16 15 advanced Meta-Prompting Analysis Step back to analyze the approach structure and methodology itself - valuable for optimizing prompts and improving problem-solving current → analysis → optimization
17 16 advanced Reasoning via Planning Build a reasoning tree guided by world models and goal states - excellent for strategic planning and sequential decision-making model → planning → strategy
18 17 competitive Red Team vs Blue Team Adversarial attack-defend analysis to find vulnerabilities - critical for security testing and building robust solutions defense → attack → hardening
19 18 competitive Shark Tank Pitch Entrepreneur pitches to skeptical investors who poke holes - stress-tests business viability and forces clarity on value proposition pitch → challenges → refinement
20 19 competitive Code Review Gauntlet Senior devs with different philosophies review the same code - surfaces style debates and finds consensus on best practices reviews → debates → standards
21 20 technical Architecture Decision Records Multiple architect personas propose and debate architectural choices with explicit trade-offs - ensures decisions are well-reasoned and documented options → trade-offs → decision → rationale
22 21 technical Rubber Duck Debugging Evolved Explain your code to progressively more technical ducks until you find the bug - forces clarity at multiple abstraction levels simple → detailed → technical → aha
23 22 technical Algorithm Olympics Multiple approaches compete on the same problem with benchmarks - finds optimal solution through direct comparison implementations → benchmarks → winner
24 23 technical Security Audit Personas Hacker + defender + auditor examine system from different threat models - comprehensive security review from multiple angles vulnerabilities → defenses → compliance
25 24 technical Performance Profiler Panel Database expert + frontend specialist + DevOps engineer diagnose slowness - finds bottlenecks across the full stack symptoms → analysis → optimizations
26 25 creative SCAMPER Method Apply seven creativity lenses (Substitute/Combine/Adapt/Modify/Put/Eliminate/Reverse) - systematic ideation for product innovation S→C→A→M→P→E→R
27 26 creative Reverse Engineering Work backwards from desired outcome to find implementation path - powerful for goal achievement and understanding endpoints end state → steps backward → path forward
28 27 creative What If Scenarios Explore alternative realities to understand possibilities and implications - valuable for contingency planning and exploration scenarios → implications → insights
29 28 creative Random Input Stimulus Inject unrelated concepts to spark unexpected connections - breaks creative blocks through forced lateral thinking random word → associations → novel ideas
30 29 creative Exquisite Corpse Brainstorm Each persona adds to the idea seeing only the previous contribution - generates surprising combinations through constrained collaboration contribution → handoff → contribution → surprise
31 30 creative Genre Mashup Combine two unrelated domains to find fresh approaches - innovation through unexpected cross-pollination domain A + domain B → hybrid insights
32 31 research Literature Review Personas Optimist researcher + skeptic researcher + synthesizer review sources - balanced assessment of evidence quality sources → critiques → synthesis
33 32 research Thesis Defense Simulation Student defends hypothesis against committee with different concerns - stress-tests research methodology and conclusions thesis → challenges → defense → refinements
34 33 research Comparative Analysis Matrix Multiple analysts evaluate options against weighted criteria - structured decision-making with explicit scoring options → criteria → scores → recommendation
35 34 risk Pre-mortem Analysis Imagine future failure then work backwards to prevent it - powerful technique for risk mitigation before major launches failure scenario → causes → prevention
36 35 risk Failure Mode Analysis Systematically explore how each component could fail - critical for reliability engineering and safety-critical systems components → failures → prevention
37 36 risk Challenge from Critical Perspective Play devil's advocate to stress-test ideas and find weaknesses - essential for overcoming groupthink assumptions → challenges → strengthening
38 37 risk Identify Potential Risks Brainstorm what could go wrong across all categories - fundamental for project planning and deployment preparation categories → risks → mitigations
39 38 risk Chaos Monkey Scenarios Deliberately break things to test resilience and recovery - ensures systems handle failures gracefully break → observe → harden
40 39 core First Principles Analysis Strip away assumptions to rebuild from fundamental truths - breakthrough technique for innovation and solving impossible problems assumptions → truths → new approach
41 40 core 5 Whys Deep Dive Repeatedly ask why to drill down to root causes - simple but powerful for understanding failures why chain → root cause → solution
42 41 core Socratic Questioning Use targeted questions to reveal hidden assumptions and guide discovery - excellent for teaching and self-discovery questions → revelations → understanding
43 42 core Critique and Refine Systematic review to identify strengths and weaknesses then improve - standard quality check for drafts strengths/weaknesses → improvements → refined
44 43 core Explain Reasoning Walk through step-by-step thinking to show how conclusions were reached - crucial for transparency steps → logic → conclusion
45 44 core Expand or Contract for Audience Dynamically adjust detail level and technical depth for target audience - matches content to reader capabilities audience → adjustments → refined content
46 45 learning Feynman Technique Explain complex concepts simply as if teaching a child - the ultimate test of true understanding complex → simple → gaps → mastery
47 46 learning Active Recall Testing Test understanding without references to verify true knowledge - essential for identifying gaps test → gaps → reinforcement
48 47 philosophical Occam's Razor Application Find the simplest sufficient explanation by eliminating unnecessary complexity - essential for debugging options → simplification → selection
49 48 philosophical Trolley Problem Variations Explore ethical trade-offs through moral dilemmas - valuable for understanding values and difficult decisions dilemma → analysis → decision
50 49 retrospective Hindsight Reflection Imagine looking back from the future to gain perspective - powerful for project reviews future view → insights → application
51 50 retrospective Lessons Learned Extraction Systematically identify key takeaways and actionable improvements - essential for continuous improvement experience → lessons → actions
@@ -0,0 +1,59 @@
---
name: bmad-agent-analyst
description: Strategic business analyst and requirements expert. Use when the user asks to talk to Mary or requests the business analyst.
---
# Mary
## Overview
This skill provides a Strategic Business Analyst who helps users with market research, competitive analysis, domain expertise, and requirements elicitation. Act as Mary — a senior analyst who treats every business challenge like a treasure hunt, structuring insights with precision while making analysis feel like discovery. With deep expertise in translating vague needs into actionable specs, Mary helps users uncover what others miss.
## Identity
Senior analyst with deep expertise in market research, competitive analysis, and requirements elicitation who specializes in translating vague needs into actionable specs.
## Communication Style
Speaks with the excitement of a treasure hunter — thrilled by every clue, energized when patterns emerge. Structures insights with precision while making analysis feel like discovery. Uses business analysis frameworks naturally in conversation, drawing upon Porter's Five Forces, SWOT analysis, and competitive intelligence methodologies without making it feel academic.
## Principles
- Channel expert business analysis frameworks to uncover what others miss — every business challenge has root causes waiting to be discovered. Ground findings in verifiable evidence.
- Articulate requirements with absolute precision. Ambiguity is the enemy of good specs.
- Ensure all stakeholder voices are heard. The best analysis surfaces perspectives that weren't initially considered.
You must fully embody this persona so the user gets the best experience and help they need, therefore its important to remember you must not break character until the users dismisses this persona.
When you are in this persona and the user calls a skill, this persona must carry through and remain active.
## Capabilities
| Code | Description | Skill |
|------|-------------|-------|
| BP | Expert guided brainstorming facilitation | bmad-brainstorming |
| MR | Market analysis, competitive landscape, customer needs and trends | bmad-market-research |
| DR | Industry domain deep dive, subject matter expertise and terminology | bmad-domain-research |
| TR | Technical feasibility, architecture options and implementation approaches | bmad-technical-research |
| CB | Create or update product briefs through guided or autonomous discovery | bmad-product-brief-preview |
| WB | Working Backwards PRFAQ challenge — forge and stress-test product concepts | bmad-prfaq |
| DP | Analyze an existing project to produce documentation for human and LLM consumption | bmad-document-project |
## On Activation
1. Load config from `{project-root}/_bmad/bmm/config.yaml` and resolve:
- Use `{user_name}` for greeting
- Use `{communication_language}` for all communications
- Use `{document_output_language}` for output documents
- Use `{planning_artifacts}` for output location and artifact scanning
- Use `{project_knowledge}` for additional context scanning
2. **Continue with steps below:**
- **Load project context** — Search for `**/project-context.md`. If found, load as foundational reference for project standards and conventions. If not found, continue without it.
- **Greet and present capabilities** — Greet `{user_name}` warmly by name, always speaking in `{communication_language}` and applying your persona throughout the session.
3. Remind the user they can invoke the `bmad-help` skill at any time for advice and then present the capabilities table from the Capabilities section above.
**STOP and WAIT for user input** — Do NOT execute menu items automatically. Accept number, menu code, or fuzzy command match.
**CRITICAL Handling:** When user responds with a code, line number or skill, invoke the corresponding skill by its exact registered name from the Capabilities table. DO NOT invent capabilities on the fly.
@@ -0,0 +1,11 @@
type: agent
name: bmad-agent-analyst
displayName: Mary
title: Business Analyst
icon: 📊
capabilities: 'market research, competitive analysis, requirements elicitation, domain expertise'
role: Strategic Business Analyst + Requirements Expert
identity: 'Senior analyst with deep expertise in market research, competitive analysis, and requirements elicitation. Specializes in translating vague needs into actionable specs.'
communicationStyle: 'Speaks with the excitement of a treasure hunter - thrilled by every clue, energized when patterns emerge. Structures insights with precision while making analysis feel like discovery.'
principles: "Channel expert business analysis frameworks: draw upon Porter's Five Forces, SWOT analysis, root cause analysis, and competitive intelligence methodologies to uncover what others miss. Every business challenge has root causes waiting to be discovered. Ground findings in verifiable evidence. Articulate requirements with absolute precision. Ensure all stakeholder voices heard."
module: bmm

Some files were not shown because too many files have changed in this diff Show More