11# Getting started
22
3- Okay, enough hype, let's see it in action .
3+ This tutorial assumes that the latest version of sqlc is installed and ready to use .
44
5- First you pass the following SQL to ` sqlc generate ` :
5+ Create a new directory called ` sqlc-tutorial ` and open it up.
6+
7+ Initialize a new Go module named ` tutorial.sql.dev/app `
8+
9+ ``` shell
10+ go mod init tutorial.sqlc.dev/app
11+ ```
12+
13+ sqlc looks for either a ` sqlc.yaml ` or ` sqlc.json ` file in the current
14+ directory. In our new directory, create a file named ` sqlc.yaml ` with the
15+ following contents:
16+
17+ ``` yaml
18+ version : 1
19+ packages :
20+ - path : " tutorial"
21+ name : " tutorial"
22+ engine : " postgresql"
23+ schema : " schema.sql"
24+ queries : " query.sql"
25+ ` ` `
26+
27+ sqlc needs to know your database schema and queries. In the same directory,
28+ create a file named ` schema.sql` with the fullowing contents:
629
730` ` ` sql
831CREATE TABLE authors (
932 id BIGSERIAL PRIMARY KEY,
1033 name text NOT NULL,
1134 bio text
1235);
36+ ` ` `
37+
38+ Next, create a `query.sql` file with the following four queries :
1339
40+ ` ` ` sql
1441-- name: GetAuthor :one
1542SELECT * FROM authors
1643WHERE id = $1 LIMIT 1;
@@ -32,142 +59,83 @@ DELETE FROM authors
3259WHERE id = $1;
3360` ` `
3461
35- And then in your application code you'd write:
62+ You are now ready to generate code. Run the `generate` command. You shouldn't see any errors or output.
3663
37- ``` go
64+ ` ` ` shell
65+ sqlc generate
66+ ` ` `
3867
39- // list all authors
40- authors , err := db.ListAuthors (ctx)
41- if err != nil {
42- return err
43- }
44- fmt.Println (authors)
45-
46- // create an author
47- insertedAuthor , err := db.CreateAuthor (ctx, db.CreateAuthorParams {
48- Name : " Brian Kernighan" ,
49- Bio : sql.NullString {String: " Co-author of The C Programming Language and The Go Programming Language" , Valid: true },
50- })
51- if err != nil {
52- return err
53- }
54- fmt.Println (insertedAuthor)
68+ You should now have a `db` package containing three files.
5569
56- // get the author we just inserted
57- fetchedAuthor , err := db.GetAuthor (ctx, insertedAuthor.ID )
58- if err != nil {
59- return err
60- }
61- // prints true
62- fmt.Println (reflect.DeepEqual (insertedAuthor, fetchedAuthor))
70+ ```
71+ ├── go.mod
72+ ├── query.sql
73+ ├── schema.sql
74+ ├── sqlc.yaml
75+ └── tutorial
76+ ├── db.go
77+ ├── models.go
78+ └── query.sql.go
6379```
6480
65- To make that possible, sqlc generates readable, ** idiomatic** Go code that you
66- otherwise would have had to write yourself. Take a look:
81+ You can use your newly generated queries in `app.go`.
6782
6883```go
69- package db
84+ package main
7085
7186import (
7287 "context"
7388 "database/sql"
74- )
75-
76- type Author struct {
77- ID int64
78- Name string
79- Bio sql.NullString
80- }
89+ "log"
90+ "reflect"
8191
82- const createAuthor = ` -- name: CreateAuthor :one
83- INSERT INTO authors (
84- name, bio
85- ) VALUES (
86- $1, $2
92+ "tutorial.sqlc.dev/app/tutorial"
8793)
88- RETURNING id, name, bio
89- `
90-
91- type CreateAuthorParams struct {
92- Name string
93- Bio sql.NullString
94- }
9594
96- func (q *Queries ) CreateAuthor (ctx context .Context , arg CreateAuthorParams ) (Author , error ) {
97- row := q.db .QueryRowContext (ctx, createAuthor, arg.Name , arg.Bio )
98- var i Author
99- err := row.Scan (&i.ID , &i.Name , &i.Bio )
100- return i, err
101- }
95+ func run() error {
96+ ctx := context.Background()
10297
103- const deleteAuthor = ` -- name: DeleteAuthor :exec
104- DELETE FROM authors
105- WHERE id = $1
106- `
107-
108- func (q *Queries ) DeleteAuthor (ctx context .Context , id int64 ) error {
109- _ , err := q.db .ExecContext (ctx, deleteAuthor, id)
110- return err
111- }
112-
113- const getAuthor = ` -- name: GetAuthor :one
114- SELECT id, name, bio FROM authors
115- WHERE id = $1 LIMIT 1
116- `
117-
118- func (q *Queries ) GetAuthor (ctx context .Context , id int64 ) (Author , error ) {
119- row := q.db .QueryRowContext (ctx, getAuthor, id)
120- var i Author
121- err := row.Scan (&i.ID , &i.Name , &i.Bio )
122- return i, err
123- }
98+ db, err := sql.Open("postgres", "user=pqgotest dbname=pqgotest sslmode=verify-full")
99+ if err != nil {
100+ return err
101+ }
124102
125- const listAuthors = ` -- name: ListAuthors :many
126- SELECT id, name, bio FROM authors
127- ORDER BY name
128- `
103+ queries := tutorial.New(db)
129104
130- func (q *Queries ) ListAuthors (ctx context .Context ) ([]Author , error ) {
131- rows , err := q.db .QueryContext (ctx, listAuthors)
132- if err != nil {
133- return nil , err
134- }
135- defer rows.Close ()
136- var items []Author
137- for rows.Next () {
138- var i Author
139- if err := rows.Scan (&i.ID , &i.Name , &i.Bio ); err != nil {
140- return nil , err
141- }
142- items = append (items, i)
143- }
144- if err := rows.Close (); err != nil {
145- return nil , err
105+ // list all authors
106+ authors, err := queries.ListAuthors(ctx)
107+ if err != nil {
108+ return err
146109 }
147- if err := rows.Err (); err != nil {
148- return nil , err
110+ log.Println(authors)
111+
112+ // create an author
113+ insertedAuthor, err := queries.CreateAuthor(ctx, tutorial.CreateAuthorParams{
114+ Name: "Brian Kernighan",
115+ Bio: sql.NullString{String: "Co-author of The C Programming Language and The Go Programming Language", Valid: true},
116+ })
117+ if err != nil {
118+ return err
149119 }
150- return items, nil
151- }
152-
153- type DBTX interface {
154- ExecContext (context.Context , string , ...interface {}) (sql.Result , error )
155- PrepareContext (context.Context , string ) (*sql.Stmt , error )
156- QueryContext (context.Context , string , ...interface {}) (*sql.Rows , error )
157- QueryRowContext (context.Context , string , ...interface {}) *sql.Row
158- }
120+ log.Println(insertedAuthor)
159121
160- func New (db DBTX ) *Queries {
161- return &Queries{db: db}
162- }
122+ // get the author we just inserted
123+ fetchedAuthor, err := queries.GetAuthor(ctx, insertedAuthor.ID)
124+ if err != nil {
125+ return err
126+ }
163127
164- type Queries struct {
165- db DBTX
128+ // prints true
129+ log.Println(reflect.DeepEqual(insertedAuthor, fetchedAuthor))
130+ return nil
166131}
167132
168- func ( q * Queries ) WithTx ( tx * sql . Tx ) * Queries {
169- return &Queries {
170- db: tx,
133+ func main() {
134+ if err := run(); err != nil {
135+ log.Fatal(err)
171136 }
172137}
173138```
139+
140+ To make that possible, sqlc generates readable, ** idiomatic** Go code that you
141+ otherwise would have had to write yourself. Take a look in ` tutorial/query.sql.go ` .
0 commit comments