Compare · 001

Your first query: MySQL and SQLite

Every file of the MySQL and SQLite versions side by side, with the lines that differ marked. 2 parameter or column types differ in Go.

Configuration

sgl.yamldiffers
MySQL
SQLite
1version: 1
1version: 1
2
2
3databases:
3databases:
4 - name: tasks
4 - name: tasks
5 dialect: mysql
5 dialect: sqlite
6 migrations: db/migrations
6 migrations: db/migrations
7 queries: db/queries
7 queries: db/queries
8 go:
8 go:
9 package: store
9 package: store
10 out: internal/store
10 out: internal/store

Migrations

db/migrations/0001_init.up.sqldiffers
MySQL
SQLite
1CREATE TABLE tasks (
1CREATE TABLE tasks (
2 id BIGINT NOT NULL AUTO_INCREMENT PRIMARY KEY,
2 id INTEGER PRIMARY KEY,
3 title VARCHAR(200) NOT NULL,
3 title TEXT NOT NULL,
4 completed INT NOT NULL DEFAULT 0,
4 completed INTEGER NOT NULL DEFAULT 0,
5 created_at DATETIME NOT NULL DEFAULT CURRENT_TIMESTAMP
5 created_at TEXT NOT NULL DEFAULT CURRENT_TIMESTAMP
6);
6);
db/migrations/0001_init.down.sqlidentical
MySQL
SQLite
1DROP TABLE tasks;
1DROP TABLE tasks;

Queries

CreateTaskdiffers
MySQL · db/queries/tasks.sql
SQLite · db/queries/tasks.sql
1-- sgl.query(CreateTask, execresult)
1-- sgl.query(CreateTask, one)
2INSERT INTO tasks (title) VALUES (?);
2INSERT INTO tasks (title) VALUES (?) RETURNING id, title, completed, created_at;
ListTasksidentical
MySQL · db/queries/tasks.sql
SQLite · db/queries/tasks.sql
1-- sgl.query(ListTasks, many)
1-- sgl.query(ListTasks, many)
2SELECT id, title, completed, created_at FROM tasks ORDER BY id;
2SELECT id, title, completed, created_at FROM tasks ORDER BY id;
CompleteTaskidentical
MySQL · db/queries/tasks.sql
SQLite · db/queries/tasks.sql
1-- sgl.query(CompleteTask, execrows)
1-- sgl.query(CompleteTask, execrows)
2UPDATE tasks SET completed = 1 WHERE id = ?;
2UPDATE tasks SET completed = 1 WHERE id = ?;

What sgl generates

CreateTaskdiffers
MySQL
SQLite
1func (queries *Queries) CreateTask(ctx context.Context, title string) (sql.Result, error)
1func (queries *Queries) CreateTask(ctx context.Context, title string) (CreateTaskRow, error)
2
3type CreateTaskRow struct {
4 ID int64 `json:"id"`
5 Title string `json:"title"`
6 Completed int64 `json:"completed"`
7 CreatedAt string `json:"created_at"`
8}
ListTasksdiffers
MySQL
SQLite
1func (queries *Queries) ListTasks(ctx context.Context) ([]ListTasksRow, error)
1func (queries *Queries) ListTasks(ctx context.Context) ([]ListTasksRow, error)
2
2
3type ListTasksRow struct {
3type ListTasksRow struct {
4 ID int64 `json:"id"`
4 ID int64 `json:"id"`
5 Title string `json:"title"`
5 Title string `json:"title"`
6 Completed int32 `json:"completed"`
6 Completed int64 `json:"completed"`
7 CreatedAt time.Time `json:"created_at"`
7 CreatedAt string `json:"created_at"`
8}
8}
CompleteTaskidentical
MySQL
SQLite
1func (queries *Queries) CompleteTask(ctx context.Context, id int64) (int64, error)
1func (queries *Queries) CompleteTask(ctx context.Context, id int64) (int64, error)

The program

example.godiffers
MySQL
SQLite
1package main
1package main
2
2
3import (
3import (
4 "context"
4 "context"
5 "database/sql"
5 "database/sql"
6 "fmt"
6 "fmt"
7 "io"
7 "io"
8
8
9 "seagull.sh/seagull/examples/mysql/001_first_query/internal/store"
9 "seagull.sh/seagull/examples/sqlite/001_first_query/internal/store"
10)
10)
11
11
12// run adds two tasks, completes the first and lists them all, through the methods sgl
12// run adds two tasks, completes the first and lists them all, through the methods sgl
13// generated from db/queries/tasks.sql.
13// generated from db/queries/tasks.sql.
14//
14//
15// MySQL has no RETURNING, so CreateTask is execresult: it returns the driver's
16// sql.Result, and LastInsertId gives the AUTO_INCREMENT id MySQL assigned. The id column
17// is BIGINT, so it is an int64 like LastInsertId's result and needs no conversion.
18//
19// Takes database (*sql.DB) which is a migrated database.
15// Takes database (*sql.DB) which is a migrated database.
20// Takes output (io.Writer) which receives the task list.
16// Takes output (io.Writer) which receives the task list.
21//
17//
22// Returns error when a query fails.
18// Returns error when a query fails.
23func run(ctx context.Context, database *sql.DB, output io.Writer) error {
19func run(ctx context.Context, database *sql.DB, output io.Writer) error {
24 queries := store.New(database)
20 queries := store.New(database)
25
21
26 result, err := queries.CreateTask(ctx, "Feed the seagulls")
22 feed, err := queries.CreateTask(ctx, "Feed the seagulls")
27 if err != nil {
23 if err != nil {
28 return fmt.Errorf("creating a task: %w", err)
24 return fmt.Errorf("creating a task: %w", err)
29 }
25 }
30 feed, err := result.LastInsertId()
31 if err != nil {
32 return fmt.Errorf("reading the new task's id: %w", err)
33 }
34 if _, err := queries.CreateTask(ctx, "Count the chips"); err != nil {
26 if _, err := queries.CreateTask(ctx, "Count the chips"); err != nil {
35 return fmt.Errorf("creating a task: %w", err)
27 return fmt.Errorf("creating a task: %w", err)
36 }
28 }
37
29
38 completed, err := queries.CompleteTask(ctx, feed)
30 completed, err := queries.CompleteTask(ctx, feed.ID)
39 if err != nil {
31 if err != nil {
40 return fmt.Errorf("completing task %d: %w", feed, err)
32 return fmt.Errorf("completing task %d: %w", feed.ID, err)
41 }
33 }
42 fmt.Fprintf(output, "completed %d task\n", completed)
34 fmt.Fprintf(output, "completed %d task\n", completed)
43
35
44 tasks, err := queries.ListTasks(ctx)
36 tasks, err := queries.ListTasks(ctx)
45 if err != nil {
37 if err != nil {
46 return fmt.Errorf("listing tasks: %w", err)
38 return fmt.Errorf("listing tasks: %w", err)
47 }
39 }
48 for _, task := range tasks {
40 for _, task := range tasks {
49 fmt.Fprintf(output, "%d\t%-18s completed=%d\n", task.ID, task.Title, task.Completed)
41 fmt.Fprintf(output, "%d\t%-18s completed=%d\n", task.ID, task.Title, task.Completed)
50 }
42 }
51 return nil
43 return nil
52}
44}

Go type differences

The same SQL types map to different Go types, because each database reports them differently.

QueryFieldMySQLSQLite
ListTaskscolumn completedint32int64
ListTaskscolumn created_attime.Timestring