DEV Community

Cover image for Stop writing your SQL code inside your Go source files!
midir99
midir99

Posted on

Stop writing your SQL code inside your Go source files!

You are writing Go but you need to write some SQL, so you end up writing SQL inside your Go source code, this is not a problem as long as they are short queries, but when your queries take up more lines of code they become hard to read and to modify, besides the lack of indentation and coloring of the code make it worse.

So... What is the solution?

Keep your SQL code as SQL and your Go code as Go (don't write SQL inside Go).

For this you can use sqload!

File users.sql

-- query: FindUserById
SELECT first_name,
       last_name,
       dob,
       email
  FROM user
 WHERE id = :id;

-- query: UpdateFirstNameById
UPDATE user
   SET first_name = :first_name
 WHERE id = :id;

-- query: DeleteUserById
DELETE FROM user WHERE id = :id;
Enter fullscreen mode Exit fullscreen mode

File main.go

package main

import (
    _ "embed"
    "fmt"

    "github.com/midir99/sqload"
)

//go:embed users.sql
var sqlCode string

var Q = sqload.MustLoadFromString[struct {
    FindUserById        string `query:"FindUserById"`
    UpdateFirstNameById string `query:"UpdateFirstNameById"`
    DeleteUserById      string `query:"DeleteUserById"`
}](sqlCode)

func main() {
    fmt.Printf("- FindUserById\n%s\n\n", Q.FindUserById)
    fmt.Printf("- UpdateFirstNameById\n%s\n\n", Q.UpdateFirstNameById)
    fmt.Printf("- DeleteUserById\n%s\n\n", Q.DeleteUserById)
}
Enter fullscreen mode Exit fullscreen mode

By keeping your SQL and Go separate you get the following advantages:

  • Better support by your IDE or code editor (because you are now handling SQL code in its own file with its .sql extension).
  • Your DBA will be able to easily find the code of each query that your project is running.
  • SQL reuse, simply copy the same .sql files from one project to another.
  • Keep your Go code free of SQL queries.

sqload is a library with 100% test coverage, free of dependencies
from third parties and their documentation has many examples.

sqload is inspired by Yesql (Clojure).

https://github.com/midir99/sqload
https://pkg.go.dev/github.com/midir99/sqload

Top comments (6)

Collapse
 
soulsbane profile image
Paul Crane

This is a really interesting approach to SQL in Go. I like it! Hopefully I'll have time to play with it over the weekend. Thanks for the library and article.

Collapse
 
midir99 profile image
midir99

Thank you so much for those words, Paul. I appreciate it!!! 😄

Collapse
 
scila1996 profile image
Nguyễn Trung

Go support raw string with string is enclosed in backticks. You can put SQL query string in it.

Collapse
 
ladam0203 profile image
Ádám Lőrincz • Edited

Would not that make the software vulnerable to SQL injection?

Collapse
 
scila1996 profile image
Nguyễn Trung

No, if you use GORM, it's support RAW SQL Builder, set value to ? and pass value as argument, easy !

db.Raw("SELECT id, name, age FROM users WHERE name = ?", 3).Scan(&result)
Enter fullscreen mode Exit fullscreen mode
Thread Thread
 
ladam0203 profile image
Ádám Lőrincz

Oh, in that sense raw! My bad :)