From ac7535609db31263d787e6ac500778ba20307cdb Mon Sep 17 00:00:00 2001 From: Neil O'Toole Date: Sat, 17 Dec 2022 22:16:10 -0700 Subject: [PATCH] Yet more linting (#118) * lint fixes * lint gosec --- .golangci.yml | 2 -- cli/output/markdownw/markdownw.go | 2 +- cli/output/raww/raww.go | 2 +- cli/output/tablew/tablew.go | 4 ++-- cli/output/xlsxw/xlsxw.go | 2 +- cli/output/xmlw/xmlw.go | 2 +- drivers/csv/csv.go | 2 +- drivers/postgres/internal_test.go | 11 +++++++++++ drivers/postgres/postgres.go | 26 +++++++++++++++++--------- drivers/sqlite3/sqlite3.go | 5 ----- drivers/sqlserver/sqlserver.go | 1 - libsq/core/stringz/stringz.go | 2 +- libsq/driver/record.go | 3 ++- testh/record.go | 2 +- testh/testh.go | 2 +- 15 files changed, 40 insertions(+), 28 deletions(-) diff --git a/.golangci.yml b/.golangci.yml index f3cefb07..80a6e502 100644 --- a/.golangci.yml +++ b/.golangci.yml @@ -301,5 +301,3 @@ issues: - gosec - noctx - wrapcheck - - diff --git a/cli/output/markdownw/markdownw.go b/cli/output/markdownw/markdownw.go index 59d502bf..870eac95 100644 --- a/cli/output/markdownw/markdownw.go +++ b/cli/output/markdownw/markdownw.go @@ -89,7 +89,7 @@ func (w *RecordWriter) writeRecord(rec sqlz.Record) error { case *[]byte: s = base64.StdEncoding.EncodeToString(*val) case *time.Time: - switch w.recMeta[i].Kind() { + switch w.recMeta[i].Kind() { //nolint:exhaustive default: s = val.Format(stringz.DatetimeFormat) case kind.Time: diff --git a/cli/output/raww/raww.go b/cli/output/raww/raww.go index 844417e0..21720d05 100644 --- a/cli/output/raww/raww.go +++ b/cli/output/raww/raww.go @@ -60,7 +60,7 @@ func (w *recordWriter) WriteRecords(recs []sqlz.Record) error { case *float64: fmt.Fprint(w.out, stringz.FormatFloat(*val)) case *time.Time: - switch w.recMeta[i].Kind() { + switch w.recMeta[i].Kind() { //nolint:exhaustive default: fmt.Fprint(w.out, val.Format(stringz.DatetimeFormat)) case kind.Time: diff --git a/cli/output/tablew/tablew.go b/cli/output/tablew/tablew.go index b3be84a4..f7bca95a 100644 --- a/cli/output/tablew/tablew.go +++ b/cli/output/tablew/tablew.go @@ -35,7 +35,7 @@ type table struct { tblImpl *internal.Table } -func (t *table) renderResultCell(knd kind.Kind, val any) string { +func (t *table) renderResultCell(knd kind.Kind, val any) string { //nolint:funlen switch val := val.(type) { case string: return val @@ -159,7 +159,7 @@ func (t *table) renderResultCell(knd kind.Kind, val any) string { } var s string - switch knd { + switch knd { //nolint:exhaustive default: s = val.Format(stringz.DatetimeFormat) case kind.Time: diff --git a/cli/output/xlsxw/xlsxw.go b/cli/output/xlsxw/xlsxw.go index 71d9a1b2..e70eab26 100644 --- a/cli/output/xlsxw/xlsxw.go +++ b/cli/output/xlsxw/xlsxw.go @@ -88,7 +88,7 @@ func (w *recordWriter) WriteRecords(recs []sqlz.Record) error { case *float64: cell.SetFloat(*val) case *time.Time: - switch w.recMeta[i].Kind() { + switch w.recMeta[i].Kind() { //nolint:exhaustive default: cell.SetDateTime(*val) case kind.Date: diff --git a/cli/output/xmlw/xmlw.go b/cli/output/xmlw/xmlw.go index 36cab939..ada7c708 100644 --- a/cli/output/xmlw/xmlw.go +++ b/cli/output/xmlw/xmlw.go @@ -196,7 +196,7 @@ func (w *recordWriter) writeRecord(rec sqlz.Record) error { case *float64: w.fieldPrintFns[i](w.outBuf, stringz.FormatFloat(*val)) case *time.Time: - switch w.recMeta[i].Kind() { + switch w.recMeta[i].Kind() { //nolint:exhaustive default: w.fieldPrintFns[i](w.outBuf, val.Format(stringz.DatetimeFormat)) case kind.Time: diff --git a/drivers/csv/csv.go b/drivers/csv/csv.go index 16dd7616..1d52c23d 100644 --- a/drivers/csv/csv.go +++ b/drivers/csv/csv.go @@ -34,7 +34,7 @@ type Provider struct { // DriverFor implements driver.Provider. func (d *Provider) DriverFor(typ source.Type) (driver.Driver, error) { - switch typ { + switch typ { //nolint:exhaustive case TypeCSV: return &driveri{log: d.Log, typ: TypeCSV, scratcher: d.Scratcher, files: d.Files}, nil case TypeTSV: diff --git a/drivers/postgres/internal_test.go b/drivers/postgres/internal_test.go index a9fd42e8..5915f62e 100644 --- a/drivers/postgres/internal_test.go +++ b/drivers/postgres/internal_test.go @@ -44,3 +44,14 @@ func TestReplacePlaceholders(t *testing.T) { require.Equal(t, want, got) } } + +func Test_idSanitize(t *testing.T) { + testCases := map[string]string{ + `tbl_name`: `"tbl_name"`, + } + + for input, want := range testCases { + got := idSanitize(input) + require.Equal(t, want, got) + } +} diff --git a/drivers/postgres/postgres.go b/drivers/postgres/postgres.go index 84307de0..4ae23c3e 100644 --- a/drivers/postgres/postgres.go +++ b/drivers/postgres/postgres.go @@ -8,6 +8,7 @@ import ( "strconv" "strings" + "github.com/jackc/pgx/v4" // Import jackc/pgx, which is our postgres driver. _ "github.com/jackc/pgx/v4/stdlib" "github.com/neilotoole/lg" @@ -137,26 +138,25 @@ func (d *driveri) Truncate(ctx context.Context, src *source.Source, tbl string, // https://www.postgresql.org/docs/9.1/sql-truncate.html // RESTART IDENTITY and CASCADE/RESTRICT are from pg 8.2 onwards - // TODO: should first check the pg version for < pg8.2 support + // FIXME: should first check the pg version for < pg8.2 support db, err := sql.Open(dbDrvr, src.Location) if err != nil { return affected, errz.Err(err) } - truncateQuery := fmt.Sprintf("TRUNCATE TABLE %q", tbl) - if reset { - // if reset & src.DBVersion >= 8.2 - truncateQuery += " RESTART IDENTITY" // default is CONTINUE IDENTITY - } - // We could add RESTRICT here; alternative is CASCADE - - affectedQuery := fmt.Sprintf("SELECT COUNT(*) FROM %q", tbl) + affectedQuery := "SELECT COUNT(*) FROM " + idSanitize(tbl) err = db.QueryRowContext(ctx, affectedQuery).Scan(&affected) if err != nil { return 0, errz.Err(err) } + truncateQuery := "TRUNCATE TABLE " + idSanitize(tbl) + if reset { + // if reset & src.DBVersion >= 8.2 + truncateQuery += " RESTART IDENTITY" // default is CONTINUE IDENTITY + } + // We could add RESTRICT here; alternative is CASCADE _, err = db.ExecContext(ctx, truncateQuery) if err != nil { return 0, errz.Err(err) @@ -165,6 +165,14 @@ func (d *driveri) Truncate(ctx context.Context, src *source.Source, tbl string, return affected, nil } +// idSanitize sanitizes an identifier (such as table name). It will +// add surrounding quotes. For example: +// +// table_name --> "table_name" +func idSanitize(s string) string { + return pgx.Identifier([]string{s}).Sanitize() +} + // CreateTable implements driver.SQLDriver. func (d *driveri) CreateTable(ctx context.Context, db sqlz.DB, tblDef *sqlmodel.TableDef) error { stmt := buildCreateTableStmt(tblDef) diff --git a/drivers/sqlite3/sqlite3.go b/drivers/sqlite3/sqlite3.go index 0f91f677..60854541 100644 --- a/drivers/sqlite3/sqlite3.go +++ b/drivers/sqlite3/sqlite3.go @@ -488,12 +488,7 @@ func (d *database) Close() error { d.closeMu.Lock() defer d.closeMu.Unlock() - //if !d.closed { - // debug.PrintStack() - //} - if d.closed { - //panic( "SQLITE DB already closed") d.log.Warnf("SQLite DB already closed: %v", d.src) return nil } diff --git a/drivers/sqlserver/sqlserver.go b/drivers/sqlserver/sqlserver.go index cfafc0d8..8c9beb70 100644 --- a/drivers/sqlserver/sqlserver.go +++ b/drivers/sqlserver/sqlserver.go @@ -147,7 +147,6 @@ func (d *driveri) Ping(ctx context.Context, src *source.Source) error { //nolint:lll func (d *driveri) Truncate(ctx context.Context, src *source.Source, tbl string, reset bool) (affected int64, err error) { - // https://docs.microsoft.com/en-us/sql/t-sql/statements/truncate-table-transact-sql?view=sql-server-ver15 // When there are foreign key constraints on mssql tables, diff --git a/libsq/core/stringz/stringz.go b/libsq/core/stringz/stringz.go index a7351e43..f61190a7 100644 --- a/libsq/core/stringz/stringz.go +++ b/libsq/core/stringz/stringz.go @@ -199,7 +199,7 @@ func stringWithCharset(length int, charset string) string { b := make([]byte, length) for i := range b { - b[i] = charset[rand.Intn(len(charset))] + b[i] = charset[rand.Intn(len(charset))] //#nosec G404 // Doesn't need to be strongly random } return string(b) diff --git a/libsq/driver/record.go b/libsq/driver/record.go index 85659459..562f2fde 100644 --- a/libsq/driver/record.go +++ b/libsq/driver/record.go @@ -108,7 +108,8 @@ func (x *StmtExecer) Close() error { // copied directly into rec, and its index is returned in skipped. // The caller must take appropriate action to deal with all // elements of rec listed in skipped. -func NewRecordFromScanRow(meta sqlz.RecordMeta, row []any, skip []int) (rec sqlz.Record, skipped []int) { +func NewRecordFromScanRow(meta sqlz.RecordMeta, row []any, skip []int) (rec sqlz.Record, + skipped []int) { //nolint:funlen rec = make([]any, len(row)) // For convenience, make a map of the skip row indices. diff --git a/testh/record.go b/testh/record.go index 0c4f04ee..efb33ee6 100644 --- a/testh/record.go +++ b/testh/record.go @@ -188,7 +188,7 @@ func CopyRecord(rec sqlz.Record) sqlz.Record { // KindScanType returns the default scan type for kind. The returned // type is typically a sql.NullType. func KindScanType(knd kind.Kind) reflect.Type { - switch knd { + switch knd { //nolint:exhaustive default: return sqlz.RTypeNullString diff --git a/testh/testh.go b/testh/testh.go index 055a1000..3da56a08 100644 --- a/testh/testh.go +++ b/testh/testh.go @@ -203,7 +203,7 @@ func (h *Helper) Source(handle string) *source.Source { require.NoError(t, err, "source %s was not found in %s", handle, testsrc.PathSrcsConfig) - switch src.Type { + switch src.Type { //nolint:exhaustive case sqlite3.Type: // This could be easily generalized for CSV/XLSX etc. fpath, err := sqlite3.PathFromLocation(src)