Skip to content

Commit

Permalink
adds mysql backend
Browse files Browse the repository at this point in the history
  • Loading branch information
tgallant committed Sep 19, 2021
1 parent bb617a8 commit 9013b84
Show file tree
Hide file tree
Showing 10 changed files with 348 additions and 1 deletion.
16 changes: 16 additions & 0 deletions .github/workflows/test.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,25 @@ on:
jobs:
test:
runs-on: ubuntu-20.04
services:
mysql:
image: mysql:8.0
env:
MYSQL_ROOT_PASSWORD: root
MYSQL_DATABASE: testing
ports:
- 3306
options: >-
--health-cmd="mysqladmin ping"
--health-interval=10s
--health-timeout=5s
--health-retries=3
steps:
- uses: actions/checkout@v2
- uses: actions/setup-go@v2
with:
go-version: "1.16.6"
- run: make test
env:
DB_URL: >-
root:root@tcp(127.0.0.1:${{ job.services.mysql.ports[3306] }})/testing
3 changes: 3 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,9 @@ ci: build_ci_image run_ci_image
test:
go test -v ./...

mysql:
./scripts/start_mysql.sh

lint: deps
./scripts/lint.sh

Expand Down
6 changes: 6 additions & 0 deletions database/driver.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package database
import (
"fmt"

"github.com/tgallant/db2jsonschema/database/mysql"
"github.com/tgallant/db2jsonschema/database/sqlite3"
"github.com/tgallant/db2jsonschema/internal/schema"
)
Expand All @@ -23,6 +24,11 @@ func NewConnection(i *ConnectionInfo) (Driver, error) {
DataSource: i.DataSource,
}
return driver, nil
case "mysql":
driver := &mysql.Driver{
DataSource: i.DataSource,
}
return driver, nil
default:
return nil, fmt.Errorf("Unknown driver: %s", i.Driver)
}
Expand Down
111 changes: 111 additions & 0 deletions database/mysql/mysql.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,111 @@
package mysql

import (
"database/sql"
"fmt"

_ "github.com/go-sql-driver/mysql"
"github.com/tgallant/db2jsonschema/internal/schema"
)

type Driver struct {
DataSource string
}

var (
typesMap = map[string]*schema.FieldType{
"bigint unsigned": {Name: "number", Format: ""},
"longtext": {Name: "string", Format: ""},
"datetime(3)": {Name: "string", Format: "date-time"},
}
)

func MapMySQLType(t string) (*schema.FieldType, error) {
schemaType, exists := typesMap[t]
if !exists {
return &schema.FieldType{}, fmt.Errorf("Unknown data type: %s", t)
}
return schemaType, nil
}

func SelectTables(conn *sql.DB) ([]string, error) {
row, err := conn.Query(`show tables`)
if err != nil {
return nil, err
}
defer row.Close()
var tables []string
for row.Next() {
var table string
err = row.Scan(&table)
if err != nil {
return nil, err
}
tables = append(tables, table)
}
return tables, nil
}

func DescribeTable(conn *sql.DB, tableName string) (*schema.Table, error) {
query := fmt.Sprintf("describe %s", tableName)
row, err := conn.Query(query)
if err != nil {
return nil, err
}
defer row.Close()
var fields []*schema.Field
for row.Next() {
var name string
var datatype string
var nullable sql.NullString
var key sql.NullString
var defaultValue sql.NullString
var extra sql.NullString
err := row.Scan(
&name,
&datatype,
&nullable,
&key,
&defaultValue,
&extra,
)
if err != nil {
return nil, err
}
fieldType, err := MapMySQLType(datatype)
if err != nil {
return nil, err
}
field := &schema.Field{
Name: name,
Type: fieldType,
}
fields = append(fields, field)
}
table := &schema.Table{
Name: tableName,
Fields: fields,
}
return table, nil
}

func (d *Driver) ReadTables() ([]*schema.Table, error) {
conn, err := sql.Open("mysql", d.DataSource)
if err != nil {
return nil, err
}
defer conn.Close()
tables, err := SelectTables(conn)
if err != nil {
return nil, err
}
var parsedTables []*schema.Table
for _, table := range tables {
parsedTable, err := DescribeTable(conn, table)
if err != nil {
return nil, err
}
parsedTables = append(parsedTables, parsedTable)
}
return parsedTables, nil
}
2 changes: 2 additions & 0 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,15 @@ go 1.16

require (
github.com/alecthomas/participle/v2 v2.0.0-alpha6
github.com/go-sql-driver/mysql v1.6.0
github.com/mattn/go-sqlite3 v1.14.8
github.com/mitchellh/go-homedir v1.1.0
github.com/sirupsen/logrus v1.2.0
github.com/spf13/cobra v1.1.3
github.com/spf13/viper v1.8.0
github.com/stretchr/testify v1.7.0
gopkg.in/yaml.v2 v2.4.0
gorm.io/driver/mysql v1.1.1
gorm.io/driver/sqlite v1.1.4
gorm.io/gorm v1.21.12
)
5 changes: 5 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,8 @@ github.com/go-gl/glfw/v3.3/glfw v0.0.0-20200222043503-6f7a984d4dc4/go.mod h1:tQ2
github.com/go-kit/kit v0.8.0/go.mod h1:xBxKIO96dXMWWy0MnWVtmwkA9/13aqxPnvrjFYMA2as=
github.com/go-logfmt/logfmt v0.3.0/go.mod h1:Qt1PoO58o5twSAckw1HlFXLmHsOX5/0LbT9GBnD5lWE=
github.com/go-logfmt/logfmt v0.4.0/go.mod h1:3RMwSq7FuexP4Kalkev3ejPJsZTpXXBr9+V4qmtdjCk=
github.com/go-sql-driver/mysql v1.6.0 h1:BCTh4TKNUYmOmMUcQ3IipzF5prigylS7XXjEkfCHuOE=
github.com/go-sql-driver/mysql v1.6.0/go.mod h1:DCzpHaOWr8IXmIStZouvnhqoel9Qv2LBy8hT2VhHyBg=
github.com/go-stack/stack v1.8.0/go.mod h1:v0f6uXyyMGvRgIKkXu+yp6POWl0qKG85gN/melR3HDY=
github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA=
github.com/gogo/protobuf v1.1.1/go.mod h1:r8qH/GZQm5c6nD/R0oafs1akxWv10x8SbQlK7atdtwQ=
Expand Down Expand Up @@ -672,9 +674,12 @@ gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b h1:h8qDotaEPuJATrMmW04NCwg7v22aHH28wwpauUhK9Oo=
gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
gorm.io/driver/mysql v1.1.1 h1:yr1bpyqiwuSPJ4aGGUX9nu46RHXlF8RASQVb1QQNcvo=
gorm.io/driver/mysql v1.1.1/go.mod h1:KdrTanmfLPPyAOeYGyG+UpDys7/7eeWT1zCq+oekYnU=
gorm.io/driver/sqlite v1.1.4 h1:PDzwYE+sI6De2+mxAneV9Xs11+ZyKV6oxD3wDGkaNvM=
gorm.io/driver/sqlite v1.1.4/go.mod h1:mJCeTFr7+crvS+TRnWc5Z3UvwxUN1BGBLMrf5LA9DYw=
gorm.io/gorm v1.20.7/go.mod h1:0HFTzE/SqkGTzK6TlDPPQbAYCluiVvhzoA1+aVyzenw=
gorm.io/gorm v1.21.9/go.mod h1:F+OptMscr0P2F2qU97WT1WimdH9GaQPoDW7AYd5i2Y0=
gorm.io/gorm v1.21.12 h1:3fQM0Eiz7jcJEhPggHEpoYnsGZqynMzverL77DV40RM=
gorm.io/gorm v1.21.12/go.mod h1:F+OptMscr0P2F2qU97WT1WimdH9GaQPoDW7AYd5i2Y0=
honnef.co/go/tools v0.0.0-20190102054323-c2f93a96b099/go.mod h1:rf3lG4BRIbNafJWhAfAdb/ePZxsR/4RtNHQocxwk9r4=
Expand Down
18 changes: 18 additions & 0 deletions scripts/start_mysql.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
#!/bin/sh

TAG=${1-8.0}

docker_exists() {
type docker > /dev/null 2> /dev/null
}

if ! docker_exists; then
echo "Docker is not installed. Please install it on your system to continue."
exit 1
fi

docker run \
-e MYSQL_ROOT_PASSWORD=root \
-e MYSQL_DATABASE=testing \
-p 3306:3306 \
"mysql:$TAG"
Loading

0 comments on commit 9013b84

Please sign in to comment.