package db import ( "context" "database/sql" _ "embed" "fmt" "log/slog" "time" "git.maximotejeda.com/maximo/tgb-user/internal/application/core/domain" _ "modernc.org/sqlite" ) //go:embed schema.sql var schema string type Adapter struct { db *sql.DB log *slog.Logger } func NewAdapter(dataSourceURL string) (*Adapter, error) { ctx, cancel := context.WithTimeout(context.Background(), 5*time.Second) defer cancel() log := slog.Default().With("adapter", "db") pragmas := "cache=shared&_foreign_keys=on&_busy_timeout=3000&_journal_mode=WAL" db, err := sql.Open("sqlite", fmt.Sprintf("file:%s?%s", dataSourceURL, pragmas)) if err != nil { return nil, fmt.Errorf("connecion error: %w", err) } err = db.PingContext(ctx) if err != nil { return nil, fmt.Errorf("ping error: %w", err) } db.SetConnMaxIdleTime(10 * time.Second) CreateTables(db) return &Adapter{db: db, log: log}, nil } // Schema func CreateTables(db *sql.DB) { _, err := db.Exec(schema) if err != nil { panic(err) } } func (a Adapter) Create(ctx context.Context, req *domain.User) (bool, error) { user := User{db: a.db, log: a.log} ok, err := user.Create(ctx, req) return ok, err } func (a Adapter) Get(ctx context.Context, id int64) (*domain.User, error) { user := NewUser(a.db, a.log) visit := NewVisits(a.db, a.log) us, err := user.Get(ctx, id) if err != nil { return nil, err } _, err1 := visit.Add(ctx, id) if err1 != nil { fmt.Println(err1) } return us, err } func (a Adapter) Edit(ctx context.Context, us *domain.User) (bool, error) { user := NewUser(a.db, a.log) ok, err := user.Edit(ctx, *us) return ok, err } func (a Adapter) Delete(ctx context.Context, id int64) (bool, error) { // TODO db work user := NewUser(a.db, a.log) ok, err := user.Delete(ctx, id) return ok, err } func (a Adapter) AddBot(ctx context.Context, tgb_id int64, botname string) (bool, error) { bu := NewBotUser(a.db, a.log) ok, err := bu.Add(ctx, tgb_id, botname) return ok, err } func (a Adapter) DeleteBot(ctx context.Context, tgb_id int64, botname string) (bool, error) { bu := NewBotUser(a.db, a.log) ok, err := bu.Delete(ctx, tgb_id, botname) return ok, err } func (a Adapter) GetBots(ctx context.Context, tgb_id int64) ([]*domain.Bot, error) { bu := NewBotUser(a.db, a.log) return bu.GetBots(ctx, tgb_id) } func (a Adapter) GetAllBotUsers(ctx context.Context, bot_name string) ([]*domain.User, error) { bu := NewBotUser(a.db, a.log) return bu.GetUsers(ctx, bot_name) } func (a Adapter) GetAllBots(ctx context.Context) ([]*domain.Bot, error) { bu := NewBotUser(a.db, a.log) return bu.GetAllBots(ctx) } // GetAccessRequest // Returns all access request from a user func (a Adapter) GetAccessRequest(ctx context.Context, tgbID int64) ([]*BotAccessRequest, error) { bar := NewBotAccessRequest(a.db, a.log) return bar.Get(ctx, tgbID) } // GetAllAccessRequest // Returns all Access request from a bot func (a Adapter) GetAllAccessRequest(ctx context.Context, botName string) ([]*BotAccessRequest, error) { bar := NewBotAccessRequest(a.db, a.log) return bar.GetAll(ctx, botName) } // CreateAccessRequest // When user try get access to a restricted bot create a row in here func (a Adapter) CreateAccessRequest(ctx context.Context, tgbID int64, botName string) (bool, error) { bar := NewBotAccessRequest(a.db, a.log) return bar.Add(ctx, tgbID, botName) } // GrantAccess // // If a row with user id and bot id is in db returns an object func (a Adapter) GrantAccess(ctx context.Context, tgbID int64, botName string) (bool, error) { bar := NewBotAccessRequest(a.db, a.log) ok, err := bar.Delete(ctx, tgbID, botName) if !ok { return false, err } else { return a.AddBot(ctx, tgbID, botName) } } // GetBannedBot // get banned bots for a user func (a Adapter) GetBannedBot(ctx context.Context, tgbID int64) ([]*BotBannedAccess, error) { bba := NewBotBannedAccess(a.db, a.log) return bba.Get(ctx, tgbID) } // GetAllBannedUsers // get all users banned from a bot func (a Adapter) GetAllBannedUsers(ctx context.Context, botName string) ([]*BotBannedAccess, error) { bba := NewBotBannedAccess(a.db, a.log) return bba.GetAll(ctx, botName) } // BanUser // ban a user creating a row in db ban and removin access request and bot grants func (a Adapter) BanUser(ctx context.Context, tgbID, until int64, botName string) (bool, error) { bba := NewBotBannedAccess(a.db, a.log) bar := NewBotAccessRequest(a.db, a.log) if ok, err := bar.Delete(ctx, tgbID, botName); !ok { a.log.Error("access request not deleted", "error", err) } if ok, err := a.DeleteBot(ctx, tgbID, botName); !ok { a.log.Error("bot access not deleted", "error", err) } return bba.Add(ctx, tgbID, until, botName) } // UnBanUser // Remove restriction from an user and create a access request func (a Adapter) UnBanUser(ctx context.Context, tgbID int64, botName string) (bool, error) { bba := NewBotBannedAccess(a.db, a.log) bar := NewBotAccessRequest(a.db, a.log) if ok, err := bba.Delete(ctx, tgbID, botName); !ok { return false, err } else { return bar.Add(ctx, tgbID, botName) } } // CreateBot // create a new bot in db func (a Adapter) CreateBot(ctx context.Context, botName string) (bool, error) { bu := NewBotUser(a.db, a.log) return bu.CreateBot(ctx, botName) }