database/sql-backed MySQL client with launcher lifecycle, health check, unit-of-work via context injection, and structured error mapping. What's included: - Executor / Tx / Client / Component interfaces using database/sql native types (sql.Result, *sql.Rows, *sql.Row) - Tx.Commit() / Tx.Rollback() without ctx, matching the honest database/sql contract - New(logger, cfg) constructor; *sql.DB opened in OnInit - Config struct with env-tag support for all pool tuning parameters - UnitOfWork via context injection; GetExecutor(ctx) returns active *sql.Tx or *sql.DB - HandleError mapping MySQLError.Number to xerrors codes (1062 → AlreadyExists, 1216/1217/1451/1452 → InvalidInput, ErrNoRows → NotFound) - Driver imported as mysqldrv alias to avoid package name collision - health.Checkable at LevelCritical; HealthCheck delegates to db.PingContext Tested-via: todo-api POC integration Reviewed-against: docs/adr/
2.3 KiB
ADR-003: Driver Import Alias to Avoid Name Collision
Status: Accepted Date: 2026-03-18
Context
The errors.go file in the mysql package uses the go-sql-driver/mysql package to type-assert MySQL error values:
import "github.com/go-sql-driver/mysql"
The Go package name of github.com/go-sql-driver/mysql is also mysql — the same as the package being authored. This creates an ambiguous identifier: within errors.go, unqualified references to mysql would be interpreted as the current package, and the driver's MySQLError type would be inaccessible without a disambiguating qualifier.
Decision
The driver is imported under the alias mysqldrv:
import mysqldrv "github.com/go-sql-driver/mysql"
In mysql.go, the driver is imported for its side effect only (registering itself with database/sql) using the blank identifier:
import _ "github.com/go-sql-driver/mysql" // register driver
The alias mysqldrv is used exclusively in errors.go, where MySQLError must be referenced by name for type assertion via errors.As:
var mysqlErr *mysqldrv.MySQLError
if errors.As(err, &mysqlErr) {
switch mysqlErr.Number { ... }
}
The alias is chosen to be recognisable — drv is a conventional abbreviation for "driver" — while making the boundary between package code and driver code immediately apparent at each call site.
Consequences
- Positive: No ambiguity between the
mysqlpackage and themysqldriver. The alias makes the distinction explicit at every use site. - Positive: The blank import in
mysql.godocuments clearly that the driver is needed only for side-effect registration. - Positive: If the driver package is ever replaced (e.g., with a fork or an alternative driver), only the import alias and the
mysqlErr.Numberswitch need to change — the rest of the package is unaffected. - Negative: Readers unfamiliar with the convention must understand that
mysqldrv.MySQLErrorrefers to the external driver, not the current package. The alias name and the import comment mitigate this. - Note: Error number constants (1062, 1216, 1217, 1451, 1452) are not exported by
go-sql-driver/mysql, so they are used as integer literals with inline comments identifying the MySQL error name (e.g.,// ER_DUP_ENTRY).