6
6
"fmt"
7
7
"io"
8
8
"os"
9
+ "path/filepath"
9
10
"strconv"
10
11
"strings"
11
12
"time"
@@ -29,11 +30,15 @@ var (
29
30
HealthTimeout = 120 * time .Second
30
31
//go:embed templates/schema.sql
31
32
initialSchema string
33
+ //go:embed templates/webhook.sql
34
+ webhookSchema string
32
35
//go:embed templates/_supabase.sql
33
36
_supabaseSchema string
37
+ //go:embed templates/restore.sh
38
+ restoreScript string
34
39
)
35
40
36
- func Run (ctx context.Context , fsys afero.Fs ) error {
41
+ func Run (ctx context.Context , fromBackup string , fsys afero.Fs ) error {
37
42
if err := utils .LoadConfigFS (fsys ); err != nil {
38
43
return err
39
44
}
@@ -43,7 +48,7 @@ func Run(ctx context.Context, fsys afero.Fs) error {
43
48
} else if ! errors .Is (err , utils .ErrNotRunning ) {
44
49
return err
45
50
}
46
- err := StartDatabase (ctx , fsys , os .Stderr )
51
+ err := StartDatabase (ctx , fromBackup , fsys , os .Stderr )
47
52
if err != nil {
48
53
if err := utils .DockerRemoveAll (context .Background (), os .Stderr , utils .Config .ProjectId ); err != nil {
49
54
fmt .Fprintln (os .Stderr , err )
@@ -86,6 +91,7 @@ cat <<'EOF' > /etc/postgresql-custom/pgsodium_root.key && \
86
91
cat <<'EOF' >> /etc/postgresql/postgresql.conf && \
87
92
docker-entrypoint.sh postgres -D /etc/postgresql
88
93
` + initialSchema + `
94
+ ` + webhookSchema + `
89
95
` + _supabaseSchema + `
90
96
EOF
91
97
` + utils .Config .Db .RootKey + `
@@ -116,7 +122,7 @@ func NewHostConfig() container.HostConfig {
116
122
return hostConfig
117
123
}
118
124
119
- func StartDatabase (ctx context.Context , fsys afero.Fs , w io.Writer , options ... func (* pgx.ConnConfig )) error {
125
+ func StartDatabase (ctx context.Context , fromBackup string , fsys afero.Fs , w io.Writer , options ... func (* pgx.ConnConfig )) error {
120
126
config := NewContainerConfig ()
121
127
hostConfig := NewHostConfig ()
122
128
networkingConfig := network.NetworkingConfig {
@@ -137,11 +143,35 @@ EOF
137
143
EOF` }
138
144
hostConfig .Tmpfs = map [string ]string {"/docker-entrypoint-initdb.d" : "" }
139
145
}
146
+ if len (fromBackup ) > 0 {
147
+ config .Entrypoint = []string {"sh" , "-c" , `
148
+ cat <<'EOF' > /etc/postgresql.schema.sql && \
149
+ cat <<'EOF' > /docker-entrypoint-initdb.d/migrate.sh && \
150
+ cat <<'EOF' > /etc/postgresql-custom/pgsodium_root.key && \
151
+ cat <<'EOF' >> /etc/postgresql/postgresql.conf && \
152
+ docker-entrypoint.sh postgres -D /etc/postgresql
153
+ ` + initialSchema + `
154
+ ` + _supabaseSchema + `
155
+ EOF
156
+ ` + restoreScript + `
157
+ EOF
158
+ ` + utils .Config .Db .RootKey + `
159
+ EOF
160
+ ` + utils .Config .Db .Settings .ToPostgresConfig () + `
161
+ EOF` }
162
+ if ! filepath .IsAbs (fromBackup ) {
163
+ fromBackup = filepath .Join (utils .CurrentDirAbs , fromBackup )
164
+ }
165
+ hostConfig .Binds = append (hostConfig .Binds , utils .ToDockerPath (fromBackup )+ ":/etc/backup.sql:ro" )
166
+ }
140
167
// Creating volume will not override existing volume, so we must inspect explicitly
141
168
_ , err := utils .Docker .VolumeInspect (ctx , utils .DbId )
142
169
utils .NoBackupVolume = client .IsErrNotFound (err )
143
170
if utils .NoBackupVolume {
144
171
fmt .Fprintln (w , "Starting database..." )
172
+ } else if len (fromBackup ) > 0 {
173
+ utils .CmdSuggestion = fmt .Sprintf ("Run %s to remove existing docker volumes." , utils .Aqua ("supabase stop --no-backup" ))
174
+ return errors .Errorf ("backup volume already exists" )
145
175
} else {
146
176
fmt .Fprintln (w , "Starting database from backup..." )
147
177
}
@@ -152,7 +182,11 @@ EOF`}
152
182
return err
153
183
}
154
184
// Initialize if we are on PG14 and there's no existing db volume
155
- if utils .NoBackupVolume {
185
+ if len (fromBackup ) > 0 {
186
+ if err := initSchema15 (ctx , utils .DbId ); err != nil {
187
+ return err
188
+ }
189
+ } else if utils .NoBackupVolume {
156
190
if err := SetupLocalDatabase (ctx , "" , fsys , w , options ... ); err != nil {
157
191
return err
158
192
}
0 commit comments