-
Notifications
You must be signed in to change notification settings - Fork 1.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Added a method to create a mysql database from a connection object #583
Changes from 2 commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -54,20 +54,22 @@ type Mysql struct { | |
config *Config | ||
} | ||
|
||
// instance must have `multiStatements` set to true | ||
func WithInstance(instance *sql.DB, config *Config) (database.Driver, error) { | ||
// connection instance must have `multiStatements` set to true | ||
func WithConnection(conn *sql.Conn, config *Config) (*Mysql, error) { | ||
if config == nil { | ||
return nil, ErrNilConfig | ||
} | ||
|
||
if err := instance.Ping(); err != nil { | ||
return nil, err | ||
mx := &Mysql{ | ||
conn: conn, | ||
db: nil, | ||
config: config, | ||
} | ||
|
||
if config.DatabaseName == "" { | ||
query := `SELECT DATABASE()` | ||
var databaseName sql.NullString | ||
if err := instance.QueryRow(query).Scan(&databaseName); err != nil { | ||
if err := conn.QueryRowContext(context.Background(), query).Scan(&databaseName); err != nil { | ||
return nil, &database.Error{OrigErr: err, Query: []byte(query)} | ||
} | ||
|
||
|
@@ -82,21 +84,31 @@ func WithInstance(instance *sql.DB, config *Config) (database.Driver, error) { | |
config.MigrationsTable = DefaultMigrationsTable | ||
} | ||
|
||
conn, err := instance.Conn(context.Background()) | ||
if err != nil { | ||
if err := mx.ensureVersionTable(); err != nil { | ||
return nil, err | ||
} | ||
|
||
mx := &Mysql{ | ||
conn: conn, | ||
db: instance, | ||
config: config, | ||
return mx, nil | ||
} | ||
|
||
// instance must have `multiStatements` set to true | ||
func WithInstance(instance *sql.DB, config *Config) (database.Driver, error) { | ||
if err := instance.Ping(); err != nil { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Move this to There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. The problem I am trying to solve is that this class does unexpected stuff to my connection pool. So the last thing I want is for If the connection I inject is not working, I expect the process to fail without side-effects on my pool. If the connection is not working, doing There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. My understanding is that connections are pooled at the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Sorry, I was misunderstanding your question. |
||
return nil, err | ||
} | ||
|
||
if err := mx.ensureVersionTable(); err != nil { | ||
conn, err := instance.Conn(context.Background()) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
mx, err := WithConnection(conn, config) | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
mx.db = instance | ||
|
||
return mx, nil | ||
} | ||
|
||
|
@@ -243,7 +255,11 @@ func (m *Mysql) Open(url string) (database.Driver, error) { | |
|
||
func (m *Mysql) Close() error { | ||
connErr := m.conn.Close() | ||
dbErr := m.db.Close() | ||
var dbErr error | ||
if m.db != nil { | ||
dbErr = m.db.Close() | ||
} | ||
|
||
if connErr != nil || dbErr != nil { | ||
return fmt.Errorf("conn: %v, db: %v", connErr, dbErr) | ||
} | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thoughts on making this context aware? Eventually, we want most DB driver methods to be context aware. I'm thinking that new methods should be context aware.
Also, unfortunately, these functions that create DB drivers currently return interfaces instead of concrete times. I'm thinking returning a concrete type as you're doing now is a cleaner pattern. Can you add a type check? e.g.
var _ database.Driver = (*Mysql)(nil) // explicit compile time type check
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If it's consistent across all drivers, then it would be a good thing. But it seems out of scope for this PR.
Sorry, I don't understand what you are asking. Where do you want this check?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh yeah, making the db drivers consistent is not in the scope of the PR. But new code should fit within the future plans/vision if possible. In this case, we should add a
ctx context.Context
parameter toWithConnection()
Add
var _ database.Driver = (*Mysql)(nil) // explicit compile time type check
as a package level ignored variable.There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK, I understood your point.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done (both of it).