SOA as document: replace export with publish workflow

Statements of Applicability are no longer exported as one-off PDFs.
Instead, each SOA owns a persistent document that accumulates versions
over time, following the same publish/approve lifecycle as authored
documents.

Publishing without approvers publishes immediately; publishing with
approvers creates a draft pending approval via the existing quorum
system. SOAs can also store default approvers that are pre-populated in
the publish dialog.

The SOA is removed from the snapshot system — applicability statements
are now queried directly (snapshot_id IS NULL) rather than through
snapshot copies.

A standalone migration script (cmd/migrate-soa-snapshots-to-documents)
converts existing SOA snapshots into documents with proper ProseMirror
content, preserving version history and approval decisions.

Signed-off-by: Sacha Al Himdani <sacha@getprobo.com>
This commit is contained in:
Sacha Al Himdani
2026-04-10 13:38:42 +02:00
parent 53edc5ba26
commit c635492f75
74 changed files with 3509 additions and 1595 deletions

View File

@@ -78,6 +78,7 @@ func NewCmdList(f *cmdutil.Factory) *cobra.Command {
flagOrderBy string
flagOrderDir string
flagQuery string
flagWriteMode string
flagDocumentType string
flagClassification string
flagStatus string
@@ -148,11 +149,21 @@ func NewCmdList(f *cmdutil.Factory) *cobra.Command {
if flagQuery != "" {
filter["query"] = flagQuery
}
if flagWriteMode != "" {
if err := cmdutil.ValidateEnum(
"write-mode",
flagWriteMode,
[]string{"AUTHORED", "GENERATED"},
); err != nil {
return err
}
filter["writeModes"] = []string{flagWriteMode}
}
if flagDocumentType != "" {
if err := cmdutil.ValidateEnum(
"document-type",
flagDocumentType,
[]string{"OTHER", "GOVERNANCE", "POLICY", "PROCEDURE", "PLAN", "REGISTER", "RECORD", "REPORT", "TEMPLATE"},
[]string{"OTHER", "GOVERNANCE", "POLICY", "PROCEDURE", "PLAN", "REGISTER", "RECORD", "REPORT", "TEMPLATE", "STATEMENT_OF_APPLICABILITY"},
); err != nil {
return err
}
@@ -261,7 +272,8 @@ func NewCmdList(f *cmdutil.Factory) *cobra.Command {
cmd.Flags().StringVar(&flagOrderBy, "order-by", "", "Order by field (TITLE, CREATED_AT, UPDATED_AT, DOCUMENT_TYPE)")
cmd.Flags().StringVar(&flagOrderDir, "order-direction", "DESC", "Sort direction (ASC, DESC)")
cmd.Flags().StringVarP(&flagQuery, "query", "q", "", "Search query")
cmd.Flags().StringVar(&flagDocumentType, "document-type", "", "Filter by document type (OTHER, GOVERNANCE, POLICY, PROCEDURE, PLAN, REGISTER, RECORD, REPORT, TEMPLATE)")
cmd.Flags().StringVar(&flagWriteMode, "write-mode", "", "Filter by write mode (AUTHORED, GENERATED)")
cmd.Flags().StringVar(&flagDocumentType, "document-type", "", "Filter by document type (OTHER, GOVERNANCE, POLICY, PROCEDURE, PLAN, REGISTER, RECORD, REPORT, TEMPLATE, STATEMENT_OF_APPLICABILITY)")
cmd.Flags().StringVar(&flagClassification, "classification", "", "Filter by classification (PUBLIC, INTERNAL, CONFIDENTIAL, SECRET)")
cmd.Flags().StringVar(&flagStatus, "status", "", "Filter by status (ACTIVE, ARCHIVED)")
flagOutput = cmdutil.AddOutputFlag(cmd)