/ scripts / gen_sqlc_docker.sh
gen_sqlc_docker.sh
 1  #!/bin/bash
 2  
 3  set -e
 4  
 5  SQLC_VERSION="1.29.0"
 6  
 7  # restore_files is a function to restore original schema files.
 8  restore_files() {
 9  	echo "Restoring SQLite bigint patch..."
10  	for file in sqldb/sqlc/migrations/*.up.sql.bak; do
11  		mv "$file" "${file%.bak}"
12  	done
13  }
14  
15  
16  # Set trap to call restore_files on script exit. This makes sure the old files
17  # are always restored.
18  trap restore_files EXIT
19  
20  # Directory of the script file, independent of where it's called from.
21  DIR="$(cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd)"
22  # Use the user's cache directories
23  GOCACHE=`go env GOCACHE`
24  GOMODCACHE=`go env GOMODCACHE`
25  
26  # SQLite doesn't support "BIGINT PRIMARY KEY" for auto-incrementing primary
27  # keys, only "INTEGER PRIMARY KEY". Internally it uses 64-bit integers for
28  # numbers anyway, independent of the column type. So we can just use
29  # "INTEGER PRIMARY KEY" and it will work the same under the hood, giving us
30  # auto incrementing 64-bit integers.
31  # _BUT_, sqlc will generate Go code with int32 if we use "INTEGER PRIMARY KEY",
32  # even though we want int64. So before we run sqlc, we need to patch the
33  # source schema SQL files to use "BIGINT PRIMARY KEY" instead of "INTEGER
34  # PRIMARY KEY".
35  echo "Applying SQLite bigint patch..."
36  for file in sqldb/sqlc/migrations/*.up.sql; do
37  	echo "Patching $file"
38  	sed -i.bak -E 's/INTEGER PRIMARY KEY/BIGINT PRIMARY KEY/g' "$file"
39  done
40  
41  echo "Generating sql models and queries in go..."
42  
43  docker run \
44    --rm \
45    --user "$UID:$(id -g)" \
46    -e UID=$UID \
47    -v "$DIR/../:/build" \
48    -w /build \
49    "sqlc/sqlc:${SQLC_VERSION}" generate
50  
51  # Because we're using the Postgres dialect of sqlc, we can't use sqlc.slice()
52  # normally, because sqlc just thinks it can pass the Golang slice directly to
53  # the database driver. So it doesn't put the /*SLICE:<field_name>*/ workaround
54  # comment into the actual SQL query. But we add the comment ourselves and now
55  # just need to replace the '$X/*SLICE:<field_name>*/' placeholders with the
56  # actual placeholder that's going to be replaced by the sqlc generated code.
57  echo "Applying sqlc.slice() workaround..."
58  for file in sqldb/sqlc/*.sql.go; do
59    echo "Patching $file"
60  
61    # First, we replace the `$X/*SLICE:<field_name>*/` placeholders with
62    # the actual placeholder that sqlc will use: `/*SLICE:<field_name>*/?`.
63    sed -i.bak -E 's/\$([0-9]+)\/\*SLICE:([a-zA-Z_][a-zA-Z0-9_]*)\*\//\/\*SLICE:\2\*\/\?/g' "$file"
64  
65    # Then, we replace the `strings.Repeat(",?", len(arg.<golang_name>))[1:]` with
66    # a function call that generates the correct number of placeholders:
67    # `makeQueryParams(len(queryParams), len(arg.<golang_name>))`.
68    sed -i.bak -E 's/strings\.Repeat\(",\?", len\(([^)]+)\)\)\[1:\]/makeQueryParams(len(queryParams), len(\1))/g' "$file"
69  
70    rm "$file.bak"
71  done