mirror of
https://github.com/SamyRai/tercul-backend.git
synced 2025-12-27 04:01:34 +00:00
195 lines
6.0 KiB
Go
195 lines
6.0 KiB
Go
package app
|
|
|
|
import (
|
|
"tercul/internal/app/auth"
|
|
"tercul/internal/app/copyright"
|
|
"tercul/internal/app/localization"
|
|
"tercul/internal/app/search"
|
|
"tercul/internal/app/work"
|
|
"tercul/internal/data/sql"
|
|
"tercul/internal/platform/cache"
|
|
"tercul/internal/platform/config"
|
|
"tercul/internal/platform/db"
|
|
"tercul/internal/platform/log"
|
|
auth_platform "tercul/internal/platform/auth"
|
|
"tercul/internal/jobs/linguistics"
|
|
|
|
"github.com/hibiken/asynq"
|
|
"github.com/weaviate/weaviate-go-client/v5/weaviate"
|
|
"gorm.io/gorm"
|
|
)
|
|
|
|
// ApplicationBuilder handles the initialization of all application components
|
|
type ApplicationBuilder struct {
|
|
dbConn *gorm.DB
|
|
redisCache cache.Cache
|
|
weaviateClient *weaviate.Client
|
|
asynqClient *asynq.Client
|
|
App *Application
|
|
linguistics *linguistics.LinguisticsFactory
|
|
}
|
|
|
|
// NewApplicationBuilder creates a new ApplicationBuilder
|
|
func NewApplicationBuilder() *ApplicationBuilder {
|
|
return &ApplicationBuilder{}
|
|
}
|
|
|
|
// BuildDatabase initializes the database connection
|
|
func (b *ApplicationBuilder) BuildDatabase() error {
|
|
log.LogInfo("Initializing database connection")
|
|
dbConn, err := db.InitDB()
|
|
if err != nil {
|
|
log.LogFatal("Failed to initialize database", log.F("error", err))
|
|
return err
|
|
}
|
|
b.dbConn = dbConn
|
|
log.LogInfo("Database initialized successfully")
|
|
return nil
|
|
}
|
|
|
|
// BuildCache initializes the Redis cache
|
|
func (b *ApplicationBuilder) BuildCache() error {
|
|
log.LogInfo("Initializing Redis cache")
|
|
redisCache, err := cache.NewDefaultRedisCache()
|
|
if err != nil {
|
|
log.LogWarn("Failed to initialize Redis cache, continuing without caching", log.F("error", err))
|
|
} else {
|
|
b.redisCache = redisCache
|
|
log.LogInfo("Redis cache initialized successfully")
|
|
}
|
|
return nil
|
|
}
|
|
|
|
// BuildWeaviate initializes the Weaviate client
|
|
func (b *ApplicationBuilder) BuildWeaviate() error {
|
|
log.LogInfo("Connecting to Weaviate", log.F("host", config.Cfg.WeaviateHost))
|
|
wClient, err := weaviate.NewClient(weaviate.Config{
|
|
Scheme: config.Cfg.WeaviateScheme,
|
|
Host: config.Cfg.WeaviateHost,
|
|
})
|
|
if err != nil {
|
|
log.LogFatal("Failed to create Weaviate client", log.F("error", err))
|
|
return err
|
|
}
|
|
b.weaviateClient = wClient
|
|
log.LogInfo("Weaviate client initialized successfully")
|
|
return nil
|
|
}
|
|
|
|
// BuildBackgroundJobs initializes Asynq for background job processing
|
|
func (b *ApplicationBuilder) BuildBackgroundJobs() error {
|
|
log.LogInfo("Setting up background job processing")
|
|
redisOpt := asynq.RedisClientOpt{
|
|
Addr: config.Cfg.RedisAddr,
|
|
Password: config.Cfg.RedisPassword,
|
|
DB: config.Cfg.RedisDB,
|
|
}
|
|
b.asynqClient = asynq.NewClient(redisOpt)
|
|
log.LogInfo("Background job client initialized successfully")
|
|
return nil
|
|
}
|
|
|
|
// BuildLinguistics initializes the linguistics components
|
|
func (b *ApplicationBuilder) BuildLinguistics() error {
|
|
log.LogInfo("Initializing linguistic analyzer")
|
|
b.linguistics = linguistics.NewLinguisticsFactory(b.dbConn, b.redisCache, 4, true)
|
|
log.LogInfo("Linguistics components initialized successfully")
|
|
return nil
|
|
}
|
|
|
|
// BuildApplication initializes all application services
|
|
func (b *ApplicationBuilder) BuildApplication() error {
|
|
log.LogInfo("Initializing application layer")
|
|
|
|
// Initialize repositories
|
|
// Note: This is a simplified wiring. In a real app, you might have more complex dependencies.
|
|
workRepo := sql.NewWorkRepository(b.dbConn)
|
|
userRepo := sql.NewUserRepository(b.dbConn)
|
|
// I need to add all the other repos here. For now, I'll just add the ones I need for the services.
|
|
translationRepo := sql.NewTranslationRepository(b.dbConn)
|
|
copyrightRepo := sql.NewCopyrightRepository(b.dbConn)
|
|
authorRepo := sql.NewAuthorRepository(b.dbConn)
|
|
tagRepo := sql.NewTagRepository(b.dbConn)
|
|
categoryRepo := sql.NewCategoryRepository(b.dbConn)
|
|
|
|
|
|
// Initialize application services
|
|
workCommands := work.NewWorkCommands(workRepo, b.linguistics.GetAnalyzer())
|
|
workQueries := work.NewWorkQueries(workRepo)
|
|
|
|
jwtManager := auth_platform.NewJWTManager()
|
|
authCommands := auth.NewAuthCommands(userRepo, jwtManager)
|
|
authQueries := auth.NewAuthQueries(userRepo, jwtManager)
|
|
|
|
copyrightCommands := copyright.NewCopyrightCommands(copyrightRepo)
|
|
copyrightQueries := copyright.NewCopyrightQueries(copyrightRepo)
|
|
|
|
localizationService := localization.NewService(translationRepo)
|
|
|
|
searchService := search.NewIndexService(localizationService, translationRepo)
|
|
|
|
b.App = &Application{
|
|
WorkCommands: workCommands,
|
|
WorkQueries: workQueries,
|
|
AuthCommands: authCommands,
|
|
AuthQueries: authQueries,
|
|
CopyrightCommands: copyrightCommands,
|
|
CopyrightQueries: copyrightQueries,
|
|
Localization: localizationService,
|
|
Search: searchService,
|
|
AuthorRepo: authorRepo,
|
|
UserRepo: userRepo,
|
|
TagRepo: tagRepo,
|
|
CategoryRepo: categoryRepo,
|
|
}
|
|
|
|
log.LogInfo("Application layer initialized successfully")
|
|
return nil
|
|
}
|
|
|
|
// Build initializes all components in the correct order
|
|
func (b *ApplicationBuilder) Build() error {
|
|
if err := b.BuildDatabase(); err != nil { return err }
|
|
if err := b.BuildCache(); err != nil { return err }
|
|
if err := b.BuildWeaviate(); err != nil { return err }
|
|
if err := b.BuildBackgroundJobs(); err != nil { return err }
|
|
if err := b.BuildLinguistics(); err != nil { return err }
|
|
if err := b.BuildApplication(); err != nil { return err }
|
|
log.LogInfo("Application builder completed successfully")
|
|
return nil
|
|
}
|
|
|
|
// GetApplication returns the application container
|
|
func (b *ApplicationBuilder) GetApplication() *Application {
|
|
return b.App
|
|
}
|
|
|
|
// GetDB returns the database connection
|
|
func (b *ApplicationBuilder) GetDB() *gorm.DB {
|
|
return b.dbConn
|
|
}
|
|
|
|
// GetAsynq returns the Asynq client
|
|
func (b *ApplicationBuilder) GetAsynq() *asynq.Client {
|
|
return b.asynqClient
|
|
}
|
|
|
|
// GetLinguisticsFactory returns the linguistics factory
|
|
func (b *ApplicationBuilder) GetLinguisticsFactory() *linguistics.LinguisticsFactory {
|
|
return b.linguistics
|
|
}
|
|
|
|
// Close closes all resources
|
|
func (b *ApplicationBuilder) Close() error {
|
|
if b.asynqClient != nil {
|
|
b.asynqClient.Close()
|
|
}
|
|
if b.dbConn != nil {
|
|
sqlDB, err := b.dbConn.DB()
|
|
if err == nil {
|
|
sqlDB.Close()
|
|
}
|
|
}
|
|
return nil
|
|
}
|