ent / ent/ent

bug: concurrent migration data race in ent/atlas

Open
#4,519 0 comments 0 reactions 0 assignees View on GitHub
Dominant language
Go
Stars
17.2k
Forks
1k
PR merge metrics
No merged PRs in 30d

Description

- [x] The issue is present in the latest release.
- [x] I have searched the [issues](https://github.com/ent/ent/issues) of this repository and believe that this is not a duplicate.

## Current Behavior 😯

Commit [397ebe9](https://github.com/ent/ent/commit/397ebe9f39af0f5481eb27c58dd9a97e8bfc089c) added `schema.Table.mu` and locking around `Atlas.setupTables` to allow concurrent migrations without copying generated tables.

However, concurrent migrations still report data races when they use the shared generated schema tables, even if each migration targets a unique SQLite database (e.g. in-memory database).

## Expected Behavior 🤔

Concurrent migrations using separate databases should be race-free when the generated schema tables are shared.

## Steps to Reproduce 🕹

Our tests create a unique in-memory SQLite (modernc) database for every test, so there is an empty database state:

```go
func NewClient(tb testing.TB) *ent.Client {
tb.Helper()

db, err := database.OpenDSN(ctx, uniqueMemoryDSN())
if err != nil {
tb.Fatal(err)
}

if err := database.Migrate(ctx, db); err != nil {
tb.Fatal(err)
}

return db
}
```

Tests run in parallel, so multiple calls to `database.Migrate` execute concurrently against different databases.

Example of some of these races

```console
go test -race ./internal/...
==================
WARNING: DATA RACE
Write at 0x00000394aa38 by goroutine 27:
entgo.io/ent/dialect/sql/schema.(*Atlas).setupTables()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1100 +0x7ef
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:107 +0x70
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.TestLookupRevokedAPIKey()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/apikey_test.go:131 +0x4f
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Previous read at 0x00000394aa38 by goroutine 24:
entgo.io/ent/dialect/sql/schema.(*Atlas).realm()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:908 +0x1512
entgo.io/ent/dialect/sql/schema.(*Atlas).StateReader.func1()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:535 +0x616
ariga.io/atlas/sql/migrate.StateReaderFunc.ReadState()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/migrate/migrate.go:149 +0x558
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:692 +0x45e
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:451 +0x5d0
ariga.io/atlas/sql/sqlite.(*inspect).databases()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/inspect.go:344 +0x225
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:432 +0x158
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:622 +0x116f
entgo.io/ent/dialect/sql.ScanOne()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:19 +0x5c
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:614 +0xdd0
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).entDialect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1134 +0x307
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:598 +0x9be
entgo.io/ent/dialect/sql/schema.(*Atlas).create-fm()
:1 +0x5c
entgo.io/ent/dialect/sql/schema.CreateFunc.Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:124 +0x5c
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:112 +0x1ad
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.TestCreateAndLookupAPIKey()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/apikey_test.go:42 +0x52
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Goroutine 27 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164

Goroutine 24 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164
==================
==================
WARNING: DATA RACE
Write at 0x00000394a400 by goroutine 27:
entgo.io/ent/dialect/sql/schema.(*Atlas).setupTables()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1089 +0x2fe
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:107 +0x70
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.TestLookupRevokedAPIKey()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/apikey_test.go:131 +0x4f
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Previous read at 0x00000394a400 by goroutine 24:
entgo.io/ent/dialect/sql/schema.(*Atlas).aIndexes()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1063 +0x427
entgo.io/ent/dialect/sql/schema.(*Atlas).realm()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:896 +0x1072
entgo.io/ent/dialect/sql/schema.(*Atlas).StateReader.func1()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:535 +0x616
ariga.io/atlas/sql/migrate.StateReaderFunc.ReadState()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/migrate/migrate.go:149 +0x558
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:692 +0x45e
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:451 +0x5d0
ariga.io/atlas/sql/sqlite.(*inspect).databases()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/inspect.go:344 +0x225
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:432 +0x158
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:622 +0x116f
entgo.io/ent/dialect/sql.ScanOne()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:19 +0x5c
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:614 +0xdd0
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).entDialect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1134 +0x307
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:598 +0x9be
entgo.io/ent/dialect/sql/schema.(*Atlas).create-fm()
:1 +0x5c
entgo.io/ent/dialect/sql/schema.CreateFunc.Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:124 +0x5c
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:112 +0x1ad
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.TestCreateAndLookupAPIKey()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/apikey_test.go:42 +0x52
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Goroutine 27 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164

Goroutine 24 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164
==================
==================
WARNING: DATA RACE
Write at 0x00000394a7c8 by goroutine 37:
entgo.io/ent/dialect/sql/schema.(*Atlas).setupTables()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1100 +0x7ef
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:107 +0x70
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.newService()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/service_test.go:19 +0x4e
github.com/lrstanley/moroi/internal/auth_test.TestServiceClear()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/session_test.go:132 +0x4b
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Previous read at 0x00000394a7c8 by goroutine 26:
entgo.io/ent/dialect/sql/schema.(*Atlas).realm()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:908 +0x1512
entgo.io/ent/dialect/sql/schema.(*Atlas).StateReader.func1()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:535 +0x616
ariga.io/atlas/sql/migrate.StateReaderFunc.ReadState()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/migrate/migrate.go:149 +0x558
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:692 +0x45e
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:451 +0x5d0
ariga.io/atlas/sql/sqlite.(*inspect).databases()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/inspect.go:344 +0x225
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:432 +0x158
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:622 +0x116f
entgo.io/ent/dialect/sql.ScanOne()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:19 +0x5c
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:614 +0xdd0
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).entDialect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1134 +0x307
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:598 +0x9be
entgo.io/ent/dialect/sql/schema.(*Atlas).create-fm()
:1 +0x5c
entgo.io/ent/dialect/sql/schema.CreateFunc.Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:124 +0x5c
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:112 +0x1ad
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.TestCreateAPIKeyRejectsPastExpiry()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/apikey_test.go:114 +0x4f
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Goroutine 37 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164

Goroutine 26 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164
==================
==================
WARNING: DATA RACE
Write at 0x00000394a400 by goroutine 37:
entgo.io/ent/dialect/sql/schema.(*Atlas).setupTables()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1089 +0x2fe
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:107 +0x70
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.newService()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/service_test.go:19 +0x4e
github.com/lrstanley/moroi/internal/auth_test.TestServiceClear()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/session_test.go:132 +0x4b
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Previous read at 0x00000394a400 by goroutine 26:
entgo.io/ent/dialect/sql/schema.(*Atlas).aIndexes()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1063 +0x427
entgo.io/ent/dialect/sql/schema.(*Atlas).realm()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:896 +0x1072
entgo.io/ent/dialect/sql/schema.(*Atlas).StateReader.func1()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:535 +0x616
ariga.io/atlas/sql/migrate.StateReaderFunc.ReadState()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/migrate/migrate.go:149 +0x558
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:692 +0x45e
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:451 +0x5d0
ariga.io/atlas/sql/sqlite.(*inspect).databases()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/inspect.go:344 +0x225
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:432 +0x158
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:622 +0x116f
entgo.io/ent/dialect/sql.ScanOne()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:19 +0x5c
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:614 +0xdd0
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).entDialect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1134 +0x307
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:598 +0x9be
entgo.io/ent/dialect/sql/schema.(*Atlas).create-fm()
:1 +0x5c
entgo.io/ent/dialect/sql/schema.CreateFunc.Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:124 +0x5c
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:112 +0x1ad
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.TestCreateAPIKeyRejectsPastExpiry()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/apikey_test.go:114 +0x4f
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Goroutine 37 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164

Goroutine 26 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164
==================
==================
WARNING: DATA RACE
Write at 0x00000394a7c8 by goroutine 32:
entgo.io/ent/dialect/sql/schema.(*Atlas).setupTables()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1100 +0x7ef
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:107 +0x70
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.TestServiceRejectsInvalidSessionKeys()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/service_test.go:155 +0x52
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Previous read at 0x00000394a7c8 by goroutine 27:
entgo.io/ent/dialect/sql/schema.(*Atlas).realm()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:908 +0x1512
entgo.io/ent/dialect/sql/schema.(*Atlas).StateReader.func1()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:535 +0x616
ariga.io/atlas/sql/migrate.StateReaderFunc.ReadState()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/migrate/migrate.go:149 +0x558
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:692 +0x45e
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:451 +0x5d0
ariga.io/atlas/sql/sqlite.(*inspect).databases()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/inspect.go:344 +0x225
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:432 +0x158
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:622 +0x116f
entgo.io/ent/dialect/sql.ScanOne()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:19 +0x5c
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:614 +0xdd0
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).entDialect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1134 +0x307
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:598 +0x9be
entgo.io/ent/dialect/sql/schema.(*Atlas).create-fm()
:1 +0x5c
entgo.io/ent/dialect/sql/schema.CreateFunc.Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:124 +0x5c
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:112 +0x1ad
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/auth_test.TestLookupRevokedAPIKey()
/home/liam/go/src/github.com/lrstanley/moroi/internal/auth/apikey_test.go:131 +0x4f
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Goroutine 32 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164

Goroutine 27 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:82 +0x164
==================
--- FAIL: TestServiceWriteAndAuthContext (0.12s)
testing.go:1865: race detected during execution of test
--- FAIL: TestCreateAndLookupAPIKey (0.15s)
testing.go:1865: race detected during execution of test
--- FAIL: TestCreateAPIKeyRejectsPastExpiry (0.16s)
testing.go:1865: race detected during execution of test
--- FAIL: TestBearerOverridesCookie (0.16s)
testing.go:1865: race detected during execution of test
--- FAIL: TestServiceClear (0.17s)
testing.go:1865: race detected during execution of test
--- FAIL: TestLookupExpiredAPIKey (0.18s)
testing.go:1865: race detected during execution of test
--- FAIL: TestLookupRevokedAPIKey (0.19s)
testing.go:1865: race detected during execution of test
--- FAIL: TestServiceRejectsInvalidSessionKeys (0.21s)
testing.go:1865: race detected during execution of test
--- FAIL: TestVerifyPassword (0.10s)
testing.go:1865: race detected during execution of test
--- FAIL: TestServiceSetupIsAtomic (0.42s)
testing.go:1865: race detected during execution of test
--- FAIL: TestServiceInitialization (0.54s)
testing.go:1865: race detected during execution of test
--- FAIL: TestServiceSetupAndAuthenticate (0.68s)
testing.go:1865: race detected during execution of test
FAIL
FAIL github.com/lrstanley/moroi/internal/auth 0.895s
? github.com/lrstanley/moroi/internal/database [no test files]
? github.com/lrstanley/moroi/internal/database/ent [no test files]
? github.com/lrstanley/moroi/internal/database/ent/apikey [no test files]
? github.com/lrstanley/moroi/internal/database/ent/asset [no test files]
? github.com/lrstanley/moroi/internal/database/ent/download [no test files]
? github.com/lrstanley/moroi/internal/database/ent/downloaditem [no test files]
? github.com/lrstanley/moroi/internal/database/ent/downloadlog [no test files]
? github.com/lrstanley/moroi/internal/database/ent/downloadprogress [no test files]
? github.com/lrstanley/moroi/internal/database/ent/enttest [no test files]
? github.com/lrstanley/moroi/internal/database/ent/hook [no test files]
? github.com/lrstanley/moroi/internal/database/ent/intercept [no test files]
? github.com/lrstanley/moroi/internal/database/ent/migrate [no test files]
? github.com/lrstanley/moroi/internal/database/ent/predicate [no test files]
? github.com/lrstanley/moroi/internal/database/ent/rest [no test files]
? github.com/lrstanley/moroi/internal/database/ent/runtime [no test files]
? github.com/lrstanley/moroi/internal/database/ent/setting [no test files]
? github.com/lrstanley/moroi/internal/database/ent/template [no test files]
? github.com/lrstanley/moroi/internal/database/schema [no test files]
==================
WARNING: DATA RACE
Write at 0x0000037e60d8 by goroutine 21:
entgo.io/ent/dialect/sql/schema.(*Atlas).setupTables()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1100 +0x7ef
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:107 +0x70
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/database/schematests.TestAPIKeyCreate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/apikey_test.go:18 +0x52
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Previous read at 0x0000037e60d8 by goroutine 36:
entgo.io/ent/dialect/sql/schema.(*Atlas).realm()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:908 +0x1512
entgo.io/ent/dialect/sql/schema.(*Atlas).StateReader.func1()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:535 +0x616
ariga.io/atlas/sql/migrate.StateReaderFunc.ReadState()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/migrate/migrate.go:149 +0x558
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:692 +0x45e
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:451 +0x5d0
ariga.io/atlas/sql/sqlite.(*inspect).databases()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/inspect.go:344 +0x225
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:432 +0x158
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:622 +0x116f
entgo.io/ent/dialect/sql.ScanOne()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:19 +0x5c
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:614 +0xdd0
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).entDialect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1134 +0x307
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:598 +0x9be
entgo.io/ent/dialect/sql/schema.(*Atlas).create-fm()
:1 +0x5c
entgo.io/ent/dialect/sql/schema.CreateFunc.Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:124 +0x5c
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:112 +0x1ad
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/database/schematests.TestTemplateFlagConfigReject()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/template_test.go:111 +0x4f
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Goroutine 21 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:80 +0x164

Goroutine 36 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:80 +0x164
==================
==================
WARNING: DATA RACE
Write at 0x0000037e5aa0 by goroutine 21:
entgo.io/ent/dialect/sql/schema.(*Atlas).setupTables()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1089 +0x2fe
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:107 +0x70
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/database/schematests.TestAPIKeyCreate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/apikey_test.go:18 +0x52
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Previous read at 0x0000037e5aa0 by goroutine 36:
entgo.io/ent/dialect/sql/schema.(*Atlas).aIndexes()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1063 +0x427
entgo.io/ent/dialect/sql/schema.(*Atlas).realm()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:896 +0x1072
entgo.io/ent/dialect/sql/schema.(*Atlas).StateReader.func1()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:535 +0x616
ariga.io/atlas/sql/migrate.StateReaderFunc.ReadState()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/migrate/migrate.go:149 +0x558
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:692 +0x45e
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:451 +0x5d0
ariga.io/atlas/sql/sqlite.(*inspect).databases()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/inspect.go:344 +0x225
ariga.io/atlas/sql/sqlite.(*inspect).InspectSchema()
/home/liam/go/pkg/mod/ariga.io/atlas@v1.3.0/sql/sqlite/driver.go:432 +0x158
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).planInspect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:671 +0x32b
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:622 +0x116f
entgo.io/ent/dialect/sql.ScanOne()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:19 +0x5c
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:614 +0xdd0
entgo.io/ent/dialect/sql.ScanInt64()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:44 +0x5d
entgo.io/ent/dialect/sql.ScanInt()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/scan.go:52 +0x31d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:134 +0x327
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.exist()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:130 +0x12d
entgo.io/ent/dialect/sql/schema.(*SQLite).init()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/sqlite.go:68 +0x78
entgo.io/ent/dialect/sql/schema.(*Atlas).entDialect()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:1134 +0x307
entgo.io/ent/dialect/sql/schema.(*Atlas).create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:598 +0x9be
entgo.io/ent/dialect/sql/schema.(*Atlas).create-fm()
:1 +0x5c
entgo.io/ent/dialect/sql/schema.CreateFunc.Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/migrate.go:124 +0x5c
entgo.io/ent/dialect/sql/schema.(*Atlas).Create()
/home/liam/go/pkg/mod/entgo.io/ent@v0.14.6/dialect/sql/schema/atlas.go:112 +0x1ad
github.com/lrstanley/moroi/internal/database/ent/migrate.Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:58 +0x1b2
github.com/lrstanley/moroi/internal/database/ent/migrate.(*Schema).Create()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/ent/migrate/migrate.go:49 +0x91
github.com/lrstanley/moroi/internal/database.Migrate()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/client.go:94 +0x195
github.com/lrstanley/moroi/internal/database/schematests.NewClient()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/core.go:46 +0x144
github.com/lrstanley/moroi/internal/database/schematests.TestTemplateFlagConfigReject()
/home/liam/go/src/github.com/lrstanley/moroi/internal/database/schematests/template_test.go:111 +0x4f
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.(*T).Run.gowrap1()
/usr/local/go/src/testing/testing.go:2258 +0x38

Goroutine 21 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:80 +0x164

Goroutine 36 (running) created at:
testing.(*T).Run()
/usr/local/go/src/testing/testing.go:2258 +0xb12
testing.runTests.func1()
/usr/local/go/src/testing/testing.go:2742 +0x84
testing.tRunner()
/usr/local/go/src/testing/testing.go:2193 +0x21c
testing.runTests()
/usr/local/go/src/testing/testing.go:2740 +0x9e9
testing.(*M).Run()
/usr/local/go/src/testing/testing.go:2600 +0xf44
main.main()
_testmain.go:80 +0x164
==================
--- FAIL: TestTemplateFlagConfigReject (0.13s)
testing.go:1865: race detected during execution of test
--- FAIL: TestTemplateHostnameRegex (0.13s)
testing.go:1865: race detected during execution of test
--- FAIL: TestTemplateSeed (0.13s)
testing.go:1865: race detected during execution of test
--- FAIL: TestDownloadStatusHook (0.14s)
testing.go:1865: race detected during execution of test
--- FAIL: TestTemplateCreateBulk (0.15s)
testing.go:1865: race detected during execution of test
--- FAIL: TestTemplateJSONTextValueRoundTrip (0.16s)
testing.go:1865: race detected during execution of test
--- FAIL: TestAPIKeyCreate (0.17s)
testing.go:1865: race detected during execution of test
--- FAIL: TestDownloadProgressUniqueFilename (0.17s)
testing.go:1865: race detected during execution of test
--- FAIL: TestDownloadRetryHookNormalizesChildren (0.17s)
testing.go:1865: race detected during execution of test
--- FAIL: TestDownloadDeleteRejectsActiveDownload (0.17s)
testing.go:1865: race detected during execution of test
--- FAIL: TestTemplateDefaultUniqueness (0.19s)
testing.go:1865: race detected during execution of test
--- FAIL: TestDownloadBuildsFlagsSnapshot (0.19s)
testing.go:1865: race detected during execution of test
FAIL
FAIL github.com/lrstanley/moroi/internal/database/schematests 0.319s
```

The mutex added in `397ebe9` protects mutations within `setupTables`, but it is released before the rest of the migration proceeds. A concurrent migration can therefore:

1. Finish `setupTables`.
2. Begin reading the shared table descriptors during `realm` or `aIndexes`.
3. Allow another migration to enter `setupTables` and mutate those same descriptors.

The database connections are independent, so this does not appear to be SQLite database contention-related.

Serializing the complete `Schema.Create` call with a process-wide mutex eliminates the race for me, for now, though less ideal:

```go
migrateMu.Lock()
defer migrateMu.Unlock()

return db.Schema.Create(ctx, opts...)
```

## Your Environment 🌎

- Ent: `v0.14.6`
- Atlas: `v1.3.0`
- Go: `1.27.1`
- SQLite driver: `modernc.org/sqlite v1.58.0`

Contributor guide

Open the contributing guide

Research direction

Start in dialect/sql/schema/atlas.go, especially Atlas.setupTables, realm, aIndexes, and the migration path shown in the race trace. Reproduce with the reported concurrent SQLite migrations and go test -race ./internal/...; done means separate-database migrations using shared generated schema tables complete without race reports.

Written by the indexing model from the issue text.

Assessment

Tech stack
go, sqlite
Domain
databases
Issue type
Bug
Difficulty
4/5
Estimated time
3-5 days
Activity status
Active
Clarity
Mostly clear
Newbie friendliness
48/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.