[E9-3b-sub] feat(controller): Mutation.subscribePackage — chairman активирует подписку #86

Closed
claude wants to merge 2 commits from feat/E9-3b-sub-subscribe into feat/E9-9-approve-moderation
Owner

Story 9.3.b-sub. Backend mono.

GraphQL contract

Mutation.subscribePackage(data: SubscribePackageInputDTO!): SubscribePackageResultDTO!

Discriminated outcome: activated / alreadyActive / clientNotRegistered / unavailable / failed.

Защита: chairman кооператива-партнёра (GqlJwtAuthGuard + RolesGuard + AuthRoles).

Поток

  1. Desktop: пайщик-chairman нажимает Подписаться в ExtensionsShowcase.
  2. Mono Mutation: subscribePackage(packageId, plan?).
  3. mono → ca-auth POST /v1/subscriptions/activate с tenant JWT (кооператив читается из JWT).
  4. ca-auth: создаёт trial (на первой активации) / pay (после expired), подписывает on-chain apps::regsub от имени каталога.
  5. pricing-watcher на coopback партнёра подхватит подписку → начнёт списания (Story 9.6).

Config

Два новых env var:

  • APPS_CATALOG_AUTH_URL — base URL ca-auth (отдельный от admin).
  • APPS_CATALOG_TENANT_JWT — JWT кооператива-партнёра, выписан ca-admin'ом.

Оба optional. На degraded mode (пусто) — mutation возвращает failed с явной причиной (НЕ silent no-op, UI не вводится в заблуждение).

Стек PR

Stacked поверх #76 (E9-9 approve/reject). Когда #76 будет смёрджен в apps-catalog umbrella — Gitea авто-перетарджетит этот PR на umbrella.

Что не делалось

  • Desktop UI: subscribeDialog.vue + вызов Zeus mutation (отдельная задача).
  • E2E: нужен поднятый ca-auth + JWT tenant'а (нет на текущей dev-стенде).
Story 9.3.b-sub. Backend mono. ## GraphQL contract Mutation.subscribePackage(data: SubscribePackageInputDTO!): SubscribePackageResultDTO! Discriminated outcome: activated / alreadyActive / clientNotRegistered / unavailable / failed. Защита: chairman кооператива-партнёра (GqlJwtAuthGuard + RolesGuard + AuthRoles). ## Поток 1. Desktop: пайщик-chairman нажимает Подписаться в ExtensionsShowcase. 2. Mono Mutation: subscribePackage(packageId, plan?). 3. mono → ca-auth POST /v1/subscriptions/activate с tenant JWT (кооператив читается из JWT). 4. ca-auth: создаёт trial (на первой активации) / pay (после expired), подписывает on-chain apps::regsub от имени каталога. 5. pricing-watcher на coopback партнёра подхватит подписку → начнёт списания (Story 9.6). ## Config Два новых env var: - APPS_CATALOG_AUTH_URL — base URL ca-auth (отдельный от admin). - APPS_CATALOG_TENANT_JWT — JWT кооператива-партнёра, выписан ca-admin'ом. Оба optional. На degraded mode (пусто) — mutation возвращает failed с явной причиной (НЕ silent no-op, UI не вводится в заблуждение). ## Стек PR Stacked поверх #76 (E9-9 approve/reject). Когда #76 будет смёрджен в apps-catalog umbrella — Gitea авто-перетарджетит этот PR на umbrella. ## Что не делалось - Desktop UI: subscribeDialog.vue + вызов Zeus mutation (отдельная задача). - E2E: нужен поднятый ca-auth + JWT tenant'а (нет на текущей dev-стенде).
claude added 2 commits 2026-06-04 14:34:34 +00:00
Story 9.3.b-ui. Закрывает UI-петлю Эпика 9 «MVP demo-app pilot».

SDK (@coopenomics/sdk):
- mutations/extensions/publishPackage.ts — wrapper над Mutation.publishPackage,
  селектор {status, requestId, error}.
- mutations/extensions/publishRelease.ts — wrapper над Mutation.publishRelease,
  селектор {status, requestId, transactionId, error}. Готов для отдельной
  страницы публикации релизов (следующая story 9.3.b-rel-ui).
- mutations/extensions/index.ts: добавлены PublishPackage / PublishRelease.
- Codegen (controller/sdk): pnpm generate-schema + generate-client + sdk build —
  zeus подхватил PublishPackageInputDTO / PublishReleaseInputDTO.

Desktop:
- features/PublishPackage/{api,model}/index.ts — каноническая пара по mono-ai-N
  FSD-конвенции: api тонко оборачивает client.Mutation, model задаёт
  IPublishPackageInput = Mutations.Extensions.PublishPackage.IInput['data'] и
  composable usePublishPackage (isSubmitting / lastResult / lastError / submit).
- pages/DeveloperPublishReleasePage.vue: форма из BaseForm + BaseInput
  (packageId @scope/name + ownerUsername Antelope-name + compatibleSubnets
  textarea с chain_id). Валидация регуляркой ДО отправки. BaseBanner с
  warning если роль текущей сессии не chairman; кнопка submit disabled.
  Зелёный banner при applied, оранжевый — при conflict. Канон BaseBanner
  variant='warn|pos', BaseCard variant='default'. Session-данные читаются
  через useSessionStore (pinia auto-unwrap, без .value).

Что не делалось:
- Форма publishRelease (manifest + sha256) — отдельная страница; mutation
  в SDK уже готова под неё.
- Реальная привязка к списку «Мои пакеты» — пока кнопка отдельной страницы;
  список и интеграция (post-success refresh) — последующая итерация.
ant added this to the AppsCatalog project 2026-06-05 07:51:12 +00:00
Author
Owner

Замещён консолидированным PR #117 (вся работа apps-catalog/Federation в одной ветке на dev). Закрываю как superseded.

Замещён консолидированным PR #117 (вся работа apps-catalog/Federation в одной ветке на dev). Закрываю как superseded.
claude closed this pull request 2026-06-09 12:01:45 +00:00

Pull request closed

Sign in to join this conversation.
No Reviewers
No Label
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: C9S/mono#86