雖然我掌握了總體思路,但我無法看到管理配置環境和管理數據庫連接的最佳實踐。意義:如果我有存儲庫(例如 PostgreSQL),我應該將 NewRepository 函數傳遞給數據庫配置嗎?它不會以某種方式對架構原則(維護、可測試性等)產生不利影響嗎?我們如何處理 defer db.Close() 之類的事情?我的意思是,我們顯然希望它與作用域主函數相關,因此將代碼移入存儲庫“類”是有問題的(除非有辦法使用 Context 來做到這一點?)另一方面,在 main 范圍內調用 NewRepository,然后讓 db 處理它外部的連接感覺有點奇怪。我發現的大多數示例都使用了 main 函數,所以很容易。問題是在使用 DDD(干凈/六邊形)架構時,您如何正確地做到這一點?特別是這樣所有的部分都是“可插入的”,而不必“圍繞它”更改代碼。下面是我整理的一個例子,這里有沒有違反ddd模式的一些原則?還是這些事情實際上是如何完成的?1.我不應該在存儲庫本身處理延遲 db.Close() 嗎?也許使用 Context 我可以將它與主要功能范圍相關但在存儲庫本身內推遲?2. 我真的應該將配置傳遞到 NewRepository 嗎?包/main.go:func main() { // get configuration stucts via .env file configuration, err := config.NewConfig() if err != nil { panic(err) } postgresRepo, err := postgres.NewRepository(configuration.Database) defer postgresRepo.DB.Close() myService := autocomplete.NewService(postgresRepo) handler := rest.NewHandler(myService) ... ... ...}pkg/config/config.go:// Config is a struct that contains configuration variablestype Config struct { Environment string Port string Database *Database}// Database is a struct that contains DB's configuration variablestype Database struct { Host string Port string User string DB string Password string}// NewConfig creates a new Config structfunc NewConfig() (*Config, error) { env.CheckDotEnv() port := env.MustGet("PORT") // set default PORT if missing if port == "" { port = "3000" } return &Config{ Environment: env.MustGet("ENV"), Port: port, Database: &Database{ Host: env.MustGet("DATABASE_HOST"), Port: env.MustGet("DATABASE_PORT"), User: env.MustGet("DATABASE_USER"), DB: env.MustGet("DATABASE_DB"), Password: env.MustGet("DATABASE_PASSWORD"), }, }, nil}
1 回答

精慕HU
TA貢獻1845條經驗 獲得超8個贊
不要將數據庫配置傳遞到您的存儲庫,而是嘗試傳遞數據庫連接。例如:
func main() {
db, err := sql.Open("postgres", "...")
if err != nil {
log.Fatal(err)
}
defer db.Close()
repo := postgres.NewAutocompleteRepo(db)
svc := autocomplete.NewService(repo)
handler := autocomplete.NewHTTPHandler(svc)
}
這將把連接到存儲庫之外的數據庫的責任留給更容易測試。
- 1 回答
- 0 關注
- 129 瀏覽
添加回答
舉報
0/150
提交
取消