package mongo import ( "context" "time" "github.com/tech/sendico/ledger/storage" "github.com/tech/sendico/ledger/storage/mongo/store" "github.com/tech/sendico/pkg/db" "github.com/tech/sendico/pkg/db/transaction" "github.com/tech/sendico/pkg/merrors" "github.com/tech/sendico/pkg/mlogger" "go.mongodb.org/mongo-driver/mongo" "go.uber.org/zap" ) type Store struct { logger mlogger.Logger conn *db.MongoConnection db *mongo.Database txFactory transaction.Factory accounts storage.AccountsStore journalEntries storage.JournalEntriesStore postingLines storage.PostingLinesStore balances storage.BalancesStore outbox storage.OutboxStore } func New(logger mlogger.Logger, conn *db.MongoConnection) (*Store, error) { if conn == nil { return nil, merrors.InvalidArgument("mongo connection is nil") } client := conn.Client() if client == nil { return nil, merrors.Internal("mongo client not initialised") } db := conn.Database() txFactory := newMongoTransactionFactory(client) s := &Store{ logger: logger.Named("storage").Named("mongo"), conn: conn, db: db, txFactory: txFactory, } ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second) defer cancel() if err := s.Ping(ctx); err != nil { s.logger.Error("mongo ping failed during store init", zap.Error(err)) return nil, err } // Initialize stores accountsStore, err := store.NewAccounts(s.logger, db) if err != nil { s.logger.Error("failed to initialize accounts store", zap.Error(err)) return nil, err } journalEntriesStore, err := store.NewJournalEntries(s.logger, db) if err != nil { s.logger.Error("failed to initialize journal entries store", zap.Error(err)) return nil, err } postingLinesStore, err := store.NewPostingLines(s.logger, db) if err != nil { s.logger.Error("failed to initialize posting lines store", zap.Error(err)) return nil, err } balancesStore, err := store.NewBalances(s.logger, db) if err != nil { s.logger.Error("failed to initialize balances store", zap.Error(err)) return nil, err } outboxStore, err := store.NewOutbox(s.logger, db) if err != nil { s.logger.Error("failed to initialize outbox store", zap.Error(err)) return nil, err } s.accounts = accountsStore s.journalEntries = journalEntriesStore s.postingLines = postingLinesStore s.balances = balancesStore s.outbox = outboxStore s.logger.Info("Ledger MongoDB storage initialized") return s, nil } func (s *Store) Ping(ctx context.Context) error { return s.conn.Ping(ctx) } func (s *Store) Accounts() storage.AccountsStore { return s.accounts } func (s *Store) JournalEntries() storage.JournalEntriesStore { return s.journalEntries } func (s *Store) PostingLines() storage.PostingLinesStore { return s.postingLines } func (s *Store) Balances() storage.BalancesStore { return s.balances } func (s *Store) Outbox() storage.OutboxStore { return s.outbox } func (s *Store) Database() *mongo.Database { return s.db } func (s *Store) TransactionFactory() transaction.Factory { return s.txFactory } var _ storage.Repository = (*Store)(nil)