Skip to content

Commit 37e0b62

Browse files
committed
Merge pull request #199 from estahn/lazy-connections
feat: use lazy connections
2 parents c8ecb25 + 3130eb3 commit 37e0b62

File tree

1 file changed

+43
-34
lines changed

1 file changed

+43
-34
lines changed

postgresql/config.go

Lines changed: 43 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -119,43 +119,9 @@ func (c *Config) NewClient(database string) (*Client, error) {
119119
dbRegistryLock.Lock()
120120
defer dbRegistryLock.Unlock()
121121

122-
dsn := c.connStr(database)
123-
dbEntry, found := dbRegistry[dsn]
124-
if !found {
125-
db, err := sql.Open("postgres", dsn)
126-
if err != nil {
127-
return nil, fmt.Errorf("Error connecting to PostgreSQL server: %w", err)
128-
}
129-
130-
// We don't want to retain connection
131-
// So when we connect on a specific database which might be managed by terraform,
132-
// we don't keep opened connection in case of the db has to be dopped in the plan.
133-
db.SetMaxIdleConns(0)
134-
db.SetMaxOpenConns(c.MaxConns)
135-
136-
defaultVersion, _ := semver.Parse(defaultExpectedPostgreSQLVersion)
137-
version := &c.ExpectedVersion
138-
if defaultVersion.Equals(c.ExpectedVersion) {
139-
// Version hint not set by user, need to fingerprint
140-
version, err = fingerprintCapabilities(db)
141-
if err != nil {
142-
db.Close()
143-
return nil, fmt.Errorf("error detecting capabilities: %w", err)
144-
}
145-
}
146-
147-
dbEntry = dbRegistryEntry{
148-
db: db,
149-
version: *version,
150-
}
151-
dbRegistry[dsn] = dbEntry
152-
}
153-
154122
client := Client{
155123
config: *c,
156124
databaseName: database,
157-
db: dbEntry.db,
158-
version: dbEntry.version,
159125
}
160126

161127
return &client, nil
@@ -305,9 +271,52 @@ func (c *Config) getDatabaseUsername() string {
305271
// return their database resources. Use of QueryRow() or Exec() is encouraged.
306272
// Query() must have their rows.Close()'ed.
307273
func (c *Client) DB() *sql.DB {
274+
c.connectDB()
308275
return c.db
309276
}
310277

278+
func (c *Client) connectDB() (*Client, error) {
279+
dbRegistryLock.Lock()
280+
defer dbRegistryLock.Unlock()
281+
282+
dsn := c.config.connStr(c.databaseName)
283+
dbEntry, found := dbRegistry[dsn]
284+
if !found {
285+
db, err := sql.Open("postgres", dsn)
286+
if err != nil {
287+
return nil, fmt.Errorf("Error connecting to PostgreSQL server: %w", err)
288+
}
289+
290+
// We don't want to retain connection
291+
// So when we connect on a specific database which might be managed by terraform,
292+
// we don't keep opened connection in case of the db has to be dopped in the plan.
293+
db.SetMaxIdleConns(0)
294+
db.SetMaxOpenConns(c.config.MaxConns)
295+
296+
defaultVersion, _ := semver.Parse(defaultExpectedPostgreSQLVersion)
297+
version := &c.config.ExpectedVersion
298+
if defaultVersion.Equals(c.config.ExpectedVersion) {
299+
// Version hint not set by user, need to fingerprint
300+
version, err = fingerprintCapabilities(db)
301+
if err != nil {
302+
db.Close()
303+
return nil, fmt.Errorf("error detecting capabilities: %w", err)
304+
}
305+
}
306+
307+
dbEntry = dbRegistryEntry{
308+
db: db,
309+
version: *version,
310+
}
311+
dbRegistry[dsn] = dbEntry
312+
}
313+
314+
c.db = dbEntry.db
315+
c.version = dbEntry.version
316+
317+
return nil, nil
318+
}
319+
311320
// fingerprintCapabilities queries PostgreSQL to populate a local catalog of
312321
// capabilities. This is only run once per Client.
313322
func fingerprintCapabilities(db *sql.DB) (*semver.Version, error) {

0 commit comments

Comments
 (0)