feat: PostgreSQL driver support

This commit is contained in:
fsylvain committed 2026-10-06 13:35:10 +02:00
1 parent eb9bfabed5
commit dc5d12348c
24 files changed
+1585 -75

No files matched your search

@@ -28,14 +28,26 @@ type DumpSource interface {
Close() error
}
var dumpPreamble = []string{
"SET NAMES utf8mb4;",
"SET sql_mode = 'NO_AUTO_VALUE_ON_ZERO';",
"SET foreign_key_checks = 0;",
type dumpDialect struct {
preamble []string
postamble []string
quote func(name string) string
literal func(databaseType string, value []byte) string
tableTrailer func(table string, columns []DumpColumn) []string
}
var dumpPostamble = []string{
"SET foreign_key_checks = 1;",
var mysqlDumpDialect = dumpDialect{
preamble: []string{
"SET NAMES utf8mb4;",
"SET sql_mode = 'NO_AUTO_VALUE_ON_ZERO';",
"SET foreign_key_checks = 0;",
},
postamble: []string{
"SET foreign_key_checks = 1;",
},
quote: quoteIdentifier,
literal: sqlLiteral,
tableTrailer: func(string, []DumpColumn) []string { return nil },
}
var plainNumber = regexp.MustCompile(`^-?[0-9]+(\.[0-9]+)?([eE][+-]?[0-9]+)?$`)
@@ -50,7 +62,11 @@ var textEscapes = strings.NewReplacer(
)
func WriteDump(output io.Writer, source DumpSource) error {
if err := writeStatements(output, dumpPreamble); err != nil {
return writeDump(output, source, mysqlDumpDialect)
}
func writeDump(output io.Writer, source DumpSource, dialect dumpDialect) error {
if err := writeStatements(output, dialect.preamble); err != nil {
return err
}
tables, err := source.Tables()
@@ -58,11 +74,11 @@ func WriteDump(output io.Writer, source DumpSource) error {
return err
}
for _, table := range tables {
if err := writeTable(output, source, table); err != nil {
if err := writeTable(output, source, table, dialect); err != nil {
return err
}
}
return writeStatements(output, dumpPostamble)
return writeStatements(output, dialect.postamble)
}
func writeStatements(output io.Writer, statements []string) error {
@@ -74,7 +90,7 @@ func writeStatements(output io.Writer, statements []string) error {
return nil
}
func writeTable(output io.Writer, source DumpSource, table string) error {
func writeTable(output io.Writer, source DumpSource, table string, dialect dumpDialect) error {
create, err := source.CreateStatement(table)
if err != nil {
return err
@@ -87,39 +103,42 @@ func writeTable(output io.Writer, source DumpSource, table string) error {
return err
}
defer rows.Close()
return writeRows(output, table, rows)
return writeRows(output, table, rows, dialect)
}
func writeRows(output io.Writer, table string, rows DumpRows) error {
func writeRows(output io.Writer, table string, rows DumpRows, dialect dumpDialect) error {
columns, err := rows.Columns()
if err != nil {
return err
}
insertPrefix := insertStatementPrefix(table, columns)
insertPrefix := insertStatementPrefix(table, columns, dialect)
for rows.Next() {
values, err := rows.Values()
if err != nil {
return err
}
if _, err := fmt.Fprintf(output, "%s%s);\n", insertPrefix, joinLiterals(columns, values)); err != nil {
if _, err := fmt.Fprintf(output, "%s%s);\n", insertPrefix, joinLiterals(columns, values, dialect)); err != nil {
return err
}
}
return rows.Err()
if err := rows.Err(); err != nil {
return err
}
return writeStatements(output, dialect.tableTrailer(table, columns))
}
func insertStatementPrefix(table string, columns []DumpColumn) string {
func insertStatementPrefix(table string, columns []DumpColumn, dialect dumpDialect) string {
names := make([]string, len(columns))
for index, column := range columns {
names[index] = quoteIdentifier(column.Name)
names[index] = dialect.quote(column.Name)
}
return fmt.Sprintf("INSERT INTO %s (%s) VALUES (", quoteIdentifier(table), strings.Join(names, ","))
return fmt.Sprintf("INSERT INTO %s (%s) VALUES (", dialect.quote(table), strings.Join(names, ","))
}
func joinLiterals(columns []DumpColumn, values [][]byte) string {
func joinLiterals(columns []DumpColumn, values [][]byte, dialect dumpDialect) string {
literals := make([]string, len(columns))
for index, column := range columns {
literals[index] = sqlLiteral(column.Type, values[index])
literals[index] = dialect.literal(column.Type, values[index])
}
return strings.Join(literals, ",")
}