waitAndClean waits for stdin to close then attempts to clean up any test databases with our parent's UUID. This is best-effort. If we hit an error we exit. We log to stderr for debugging, but we don't expect this output to normally be available since the parent has exited. Uncomment the line `cmd.S
()
| 143 | // We log to stderr for debugging, but we don't expect this output to normally be available since the parent has |
| 144 | // exited. Uncomment the line `cmd.Stderr = os.Stderr` in startCleaner() to see this output. |
| 145 | func (c *cleaner) waitAndClean() { |
| 146 | c.logger.Debug(context.Background(), "waiting for stdin to close") |
| 147 | _, _ = io.ReadAll(os.Stdin) // here we're just waiting for stdin to close |
| 148 | c.logger.Debug(context.Background(), "stdin closed") |
| 149 | rows, err := c.db.Query( |
| 150 | "SELECT name FROM test_databases WHERE process_uuid = $1 AND dropped_at IS NULL", |
| 151 | c.parentUUID, |
| 152 | ) |
| 153 | if err != nil { |
| 154 | c.logger.Error(context.Background(), "error querying test databases", slog.Error(err)) |
| 155 | return |
| 156 | } |
| 157 | defer func() { |
| 158 | _ = rows.Close() |
| 159 | }() |
| 160 | names := make([]string, 0) |
| 161 | for rows.Next() { |
| 162 | var name string |
| 163 | if err := rows.Scan(&name); err != nil { |
| 164 | continue |
| 165 | } |
| 166 | names = append(names, name) |
| 167 | } |
| 168 | if closeErr := rows.Close(); closeErr != nil { |
| 169 | c.logger.Error(context.Background(), "error closing rows", slog.Error(closeErr)) |
| 170 | } |
| 171 | c.logger.Debug(context.Background(), "queried names", slog.F("names", names)) |
| 172 | for _, name := range names { |
| 173 | _, err := c.db.Exec(fmt.Sprintf("DROP DATABASE IF EXISTS %s", name)) |
| 174 | if err != nil { |
| 175 | c.logger.Error(context.Background(), "error dropping database", slog.Error(err), slog.F("name", name)) |
| 176 | return |
| 177 | } |
| 178 | _, err = c.db.Exec("UPDATE test_databases SET dropped_at = CURRENT_TIMESTAMP WHERE name = $1", name) |
| 179 | if err != nil { |
| 180 | c.logger.Error(context.Background(), "error dropping database", slog.Error(err), slog.F("name", name)) |
| 181 | return |
| 182 | } |
| 183 | } |
| 184 | c.logger.Debug(context.Background(), "finished cleaning") |
| 185 | } |
| 186 | |
| 187 | // RunCleaner runs the test database cleaning process. It takes no arguments but uses stdio and environment variables |
| 188 | // for its operation. |