Tier: Adapter · Status: Full (port + LocalStore) · Java original:
firefly-ecm· .NET project:FireflyFramework.Ecm
ecm is the framework's Enterprise Content Management abstraction.
It defines four orthogonal ports — Document, Folder,
ContentStore, ESignatureProvider — and ships a default
LocalStore (filesystem-backed ContentStore) plus an in-memory
Service composing the two for tests and single-instance deployments.
Cloud storage adapters (ecmstorageaws, ecmstorageazure) and
e-signature provider adapters (ecmesignaturedocusign,
ecmesignatureadobesign, ecmesignaturelogalty) live in dedicated
modules and ship as port-asserting stubs — see docs/AUDIT.md
§ Roadmap.
type Document struct {
ID, FolderID, Name, MimeType string
Size int64
Tags []string
Metadata map[string]any
CreatedAt, UpdatedAt time.Time
Version int
}
type Folder struct {
ID, Name, ParentID string
CreatedAt time.Time
}
type ContentStore interface {
Put(ctx, key string, r io.Reader) (size int64, err error)
Get(ctx, key string) (io.ReadCloser, error)
Delete(ctx, key string) error
Name() string
}
type DocumentService interface {
Create(ctx, doc Document, content io.Reader) (Document, error)
Get(ctx, id string) (Document, error)
Read(ctx, id string) (io.ReadCloser, error)
Delete(ctx, id string) error
}
type SignatureRequest struct { DocumentID string; Signers []string; Title, Provider string }
type SignatureStatus string // SignaturePending | SignatureSigned | SignatureDeclined | SignatureExpired
type ESignatureProvider interface {
Create(ctx, SignatureRequest) (id string, err error)
Status(ctx, id string) (SignatureStatus, error)
Cancel(ctx, id string) error
Name() string
}
var ErrNotFound = errors.New("firefly/ecm: not found")type LocalStore struct{ ... }
func NewLocalStore(root string) *LocalStore // filesystem-backed ContentStore
type Service struct{ ... }
func NewService(content ContentStore) *Service // in-memory document indeximport (
"bytes"
"context"
"github.com/fireflyframework/fireflyframework-go/ecm"
)
svc := ecm.NewService(ecm.NewLocalStore("/var/firefly/docs"))
doc, _ := svc.Create(ctx, ecm.Document{Name: "spec.pdf", MimeType: "application/pdf"}, bytes.NewReader(pdfBytes))
fmt.Println(doc.ID, doc.Size)
r, _ := svc.Read(ctx, doc.ID)
defer r.Close()
io.Copy(os.Stdout, r)
_ = svc.Delete(ctx, doc.ID)For S3-backed content storage in production, swap the LocalStore
for ecmstorageaws.New(...) (once that adapter is wired).
cd ecm
go test ./...Covers create + get + read + delete lifecycle, file-backed Read after Create, and 404-after-delete.