go.charczuk.com@v0.0.0-20240327042549-bc490516bd1a/sdk/apputil/model.go (about)

     1  /*
     2  
     3  Copyright (c) 2023 - Present. Will Charczuk. All rights reserved.
     4  Use of this source code is governed by a MIT license that can be found in the LICENSE file at the root of the repository.
     5  
     6  */
     7  
     8  package apputil
     9  
    10  import (
    11  	"context"
    12  	"fmt"
    13  	"testing"
    14  	"time"
    15  
    16  	"go.charczuk.com/sdk/assert"
    17  	"go.charczuk.com/sdk/db"
    18  	"go.charczuk.com/sdk/db/dbutil"
    19  	"go.charczuk.com/sdk/testutil"
    20  )
    21  
    22  var (
    23  	userCols          = db.TypeMetaFor(User{})
    24  	userTableName     = User{}.TableName()
    25  	sessionsTableName = Session{}.TableName()
    26  
    27  	getUserByEmailQuery        = fmt.Sprintf("SELECT %s FROM %s WHERE email = $1", db.ColumnNamesCSV(userCols.Columns()), userTableName)
    28  	deleteExpiredSessionsQuery = fmt.Sprintf("DELETE FROM %s WHERE expires_utc < $1", sessionsTableName)
    29  )
    30  
    31  // NewModelManager returns a new model manager.
    32  func NewModelManager(conn *db.Connection, opts ...db.InvocationOption) *ModelManager {
    33  	return &ModelManager{
    34  		BaseManager: dbutil.NewBaseManager(conn, opts...),
    35  	}
    36  }
    37  
    38  // ModelManager implements database functions.
    39  type ModelManager struct {
    40  	dbutil.BaseManager
    41  }
    42  
    43  // GetUserByEmail gets a user by email.
    44  func (m ModelManager) GetUserByEmail(ctx context.Context, email string) (output User, found bool, err error) {
    45  	found, err = m.Invoke(ctx, db.OptLabel("get_user_by_email")).Query(getUserByEmailQuery, email).Out(&output)
    46  	return
    47  }
    48  
    49  // DeleteExpiredSessions deletes sessions that are expired and older than 14 days.
    50  func (m ModelManager) DeleteExpiredSessions(ctx context.Context, oldest time.Time) error {
    51  	_, err := m.Invoke(ctx, db.OptLabel("delete_expired_sessions")).Exec(deleteExpiredSessionsQuery, oldest)
    52  	return err
    53  }
    54  
    55  // NewTest returns a new test context.
    56  func NewTest(t *testing.T) (*ModelManager, func()) {
    57  	tx, err := testutil.DefaultDB().BeginTx(context.Background())
    58  	assert.ItsNil(t, err)
    59  	return NewModelManager(testutil.DefaultDB(), db.OptTx(tx)), func() {
    60  		_ = tx.Rollback()
    61  	}
    62  }
    63  
    64  // CreateTestUser creates a test user.
    65  func CreateTestUser(t *testing.T, mgr *ModelManager) *User {
    66  	u0 := NewTestUser()
    67  	assert.ItsNil(t, mgr.Invoke(context.Background()).Create(&u0))
    68  	return &u0
    69  }
    70  
    71  // CreateTestSession creates a test session.
    72  func CreateTestSession(t *testing.T, mgr *ModelManager, user *User) *Session {
    73  	s0 := NewTestSession(user)
    74  	assert.ItsNil(t, mgr.Invoke(context.Background()).Create(&s0))
    75  	return &s0
    76  }