add golang-migrate

absences
William Perron 1 year ago
parent e7d12be4b8
commit aaf569cb69
Signed by: wperron
GPG Key ID: BFDB4EF72D73C5F2

@ -1,6 +1,13 @@
MIT License
The MIT License (MIT)
Original Work
Copyright (c) 2016 Matthias Kadenbach
https://github.com/mattes/migrate
Modified Work
Copyright (c) 2018 Dale Hui
https://github.com/golang-migrate/migrate
Copyright (c) 2022 William Perron
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
@ -9,13 +16,13 @@ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.

@ -1,170 +1,190 @@
# themis
Discord App to allow EU4 players to take claims on regions and provinces.
## Setup
### Requirements
To develop:
- [Go](https://go.dev/) version 1.19 or higher installed locally
- `sqlite3` installed locally (already ships by default on most OSes)
To deploy:
- Register for a [free account on Fly](https://fly.io)
- An [AWS account](https://console.aws.amazon.com)
### Steps
To work with the core modules that simply interact with the database, or make
sure that everything compiles correctly, you can run the following commands:
[![GitHub Workflow Status (branch)](https://img.shields.io/github/actions/workflow/status/golang-migrate/migrate/ci.yaml?branch=master)](https://github.com/golang-migrate/migrate/actions/workflows/ci.yaml?query=branch%3Amaster)
[![GoDoc](https://pkg.go.dev/badge/github.com/golang-migrate/migrate)](https://pkg.go.dev/github.com/golang-migrate/migrate/v4)
[![Coverage Status](https://img.shields.io/coveralls/github/golang-migrate/migrate/master.svg)](https://coveralls.io/github/golang-migrate/migrate?branch=master)
[![packagecloud.io](https://img.shields.io/badge/deb-packagecloud.io-844fec.svg)](https://packagecloud.io/golang-migrate/migrate?filter=debs)
[![Docker Pulls](https://img.shields.io/docker/pulls/migrate/migrate.svg)](https://hub.docker.com/r/migrate/migrate/)
![Supported Go Versions](https://img.shields.io/badge/Go-1.19%2C%201.20-lightgrey.svg)
[![GitHub Release](https://img.shields.io/github/release/golang-migrate/migrate.svg)](https://github.com/golang-migrate/migrate/releases)
[![Go Report Card](https://goreportcard.com/badge/github.com/golang-migrate/migrate/v4)](https://goreportcard.com/report/github.com/golang-migrate/migrate/v4)
# migrate
__Database migrations written in Go. Use as [CLI](#cli-usage) or import as [library](#use-in-your-go-project).__
* Migrate reads migrations from [sources](#migration-sources)
and applies them in correct order to a [database](#databases).
* Drivers are "dumb", migrate glues everything together and makes sure the logic is bulletproof.
(Keeps the drivers lightweight, too.)
* Database drivers don't assume things or try to correct user input. When in doubt, fail.
Forked from [mattes/migrate](https://github.com/mattes/migrate)
## Databases
Database drivers run migrations. [Add a new database?](database/driver.go)
* [PostgreSQL](database/postgres)
* [PGX v4](database/pgx)
* [PGX v5](database/pgx/v5)
* [Redshift](database/redshift)
* [Ql](database/ql)
* [Cassandra](database/cassandra)
* [SQLite](database/sqlite)
* [SQLite3](database/sqlite3) ([todo #165](https://github.com/mattes/migrate/issues/165))
* [SQLCipher](database/sqlcipher)
* [MySQL/ MariaDB](database/mysql)
* [Neo4j](database/neo4j)
* [MongoDB](database/mongodb)
* [CrateDB](database/crate) ([todo #170](https://github.com/mattes/migrate/issues/170))
* [Shell](database/shell) ([todo #171](https://github.com/mattes/migrate/issues/171))
* [Google Cloud Spanner](database/spanner)
* [CockroachDB](database/cockroachdb)
* [YugabyteDB](database/yugabytedb)
* [ClickHouse](database/clickhouse)
* [Firebird](database/firebird)
* [MS SQL Server](database/sqlserver)
### Database URLs
Database connection strings are specified via URLs. The URL format is driver dependent but generally has the form: `dbdriver://username:password@host:port/dbname?param1=true&param2=false`
Any [reserved URL characters](https://en.wikipedia.org/wiki/Percent-encoding#Percent-encoding_reserved_characters) need to be escaped. Note, the `%` character also [needs to be escaped](https://en.wikipedia.org/wiki/Percent-encoding#Percent-encoding_the_percent_character)
Explicitly, the following characters need to be escaped:
`!`, `#`, `$`, `%`, `&`, `'`, `(`, `)`, `*`, `+`, `,`, `/`, `:`, `;`, `=`, `?`, `@`, `[`, `]`
It's easiest to always run the URL parts of your DB connection URL (e.g. username, password, etc) through an URL encoder. See the example Python snippets below:
```bash
go test ./...
go build -o ./bin/ ./cmd/...
$ python3 -c 'import urllib.parse; print(urllib.parse.quote(input("String to encode: "), ""))'
String to encode: FAKEpassword!#$%&'()*+,/:;=?@[]
FAKEpassword%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D
$ python2 -c 'import urllib; print urllib.quote(raw_input("String to encode: "), "")'
String to encode: FAKEpassword!#$%&'()*+,/:;=?@[]
FAKEpassword%21%23%24%25%26%27%28%29%2A%2B%2C%2F%3A%3B%3D%3F%40%5B%5D
$
```
## Operations
This application is deployed via [Fly](https://fly.io) on a single virtual
machine instance. It uses an embed SQLite database as its database engine, and
uses [Litestream](https://litestream.io) to replicate the database to an S3
bucket.
### Application Configuration
The deployment configurations can be found in the [fly.toml](/fly.toml) file and
you can find more information on the configuration options [in the official Fly
documentation](https://fly.io/docs/reference/configuration/).
The virtual image is based off of the [Dockerfile](/Dockerfile) which is a
multi-stage build that builds the main application binary, downloads Litestream
and packages everything on top of an Ubuntu 22.04 base.
### Entrypoint
The application is started using a [custom entrypoint shell script](/start.sh)
that is in charge of first restoring the database file through Litestream and
then starting the main application as a [child process of Litestream's
replication process](https://litestream.io/reference/replicate/#arguments).
## Migration Sources
It's a very simple script but is necessary since the application doesn't have a
persistent volume to rely on and must rehydrate its database file after every
deployment.
Source drivers read migrations from local or remote sources. [Add a new source?](source/driver.go)
### Environment Variables
* [Filesystem](source/file) - read from filesystem
* [io/fs](source/iofs) - read from a Go [io/fs](https://pkg.go.dev/io/fs#FS)
* [Go-Bindata](source/go_bindata) - read from embedded binary data ([jteeuwen/go-bindata](https://github.com/jteeuwen/go-bindata))
* [pkger](source/pkger) - read from embedded binary data ([markbates/pkger](https://github.com/markbates/pkger))
* [GitHub](source/github) - read from remote GitHub repositories
* [GitHub Enterprise](source/github_ee) - read from remote GitHub Enterprise repositories
* [Bitbucket](source/bitbucket) - read from remote Bitbucket repositories
* [Gitlab](source/gitlab) - read from remote Gitlab repositories
* [AWS S3](source/aws_s3) - read from Amazon Web Services S3
* [Google Cloud Storage](source/google_cloud_storage) - read from Google Cloud Platform Storage
| Env Var | Defined At |
| ----------------------- | --------------------- |
| `DISCORD_TOKEN` | fly secret |
| `DISCORD_APP_ID` | [fly.toml](/fly.toml) |
| `DISCORD_GUILD_ID` | [fly.toml](fly.toml) |
| `AWS_ACCESS_KEY_ID` | fly secret |
| `AWS_SECRET_ACCESS_KEY` | fly secret |
## CLI usage
## Local Development
* Simple wrapper around this library.
* Handles ctrl+c (SIGINT) gracefully.
* No config search paths, no config files, no magic ENV var injections.
### Application Entrypoint
__[CLI Documentation](cmd/migrate)__
- `./cmd/themis-server` This is the main application entrypoint
- `./cmd/themis-repl` _coming soon_
### Basic usage
### Core Functions
The core database functions can be developed and tested locally easily, just run
`go test ./...` to test your changes locally.
```bash
$ migrate -source file://path/to/migrations -database postgres://localhost:5432/database up 2
```
You can also load a test database easily by using the `init.sql` script. You can
use the cli sqlite3 client or connect using whatever SQL editor you prefer that
can open sqlite3 connections.
### Docker usage
```bash
sqlite3 local.db < migrations/init.sql
sqlite3 local.db
# interactive SQLite session
$ docker run -v {{ migration dir }}:/migrations --network host migrate/migrate
-path=/migrations/ -database postgres://localhost:5432/database up 2
```
### Discord Integration
This is a work in progress, but I am currently using a dedicated Discord server
with this application already signed into it. You can contact me directly to be
invited into that server. From there you only need to set the following
environment variables before launching the `./cmd/themis-server` entrypoint:
## Use in your Go project
* API is stable and frozen for this release (v3 & v4).
* Uses [Go modules](https://golang.org/cmd/go/#hdr-Modules__module_versions__and_more) to manage dependencies.
* To help prevent database corruptions, it supports graceful stops via `GracefulStop chan bool`.
* Bring your own logger.
* Uses `io.Reader` streams internally for low memory overhead.
* Thread-safe and no goroutine leaks.
__[Go Documentation](https://pkg.go.dev/github.com/golang-migrate/migrate/v4)__
```go
import (
"github.com/golang-migrate/migrate/v4"
_ "github.com/golang-migrate/migrate/v4/database/postgres"
_ "github.com/golang-migrate/migrate/v4/source/github"
)
func main() {
m, err := migrate.New(
"github://mattes:personal-access-token@mattes/migrate_test",
"postgres://localhost:5432/database?sslmode=enable")
m.Steps(2)
}
```
```bash
export DISCORD_APP_ID="1014881815921705030"
export DISCORD_GUILD_ID="[test server id goes here]"
Want to use an existing database client?
```go
import (
"database/sql"
_ "github.com/lib/pq"
"github.com/golang-migrate/migrate/v4"
"github.com/golang-migrate/migrate/v4/database/postgres"
_ "github.com/golang-migrate/migrate/v4/source/file"
)
func main() {
db, err := sql.Open("postgres", "postgres://localhost:5432/database?sslmode=enable")
driver, err := postgres.WithInstance(db, &postgres.Config{})
m, err := migrate.NewWithDatabaseInstance(
"file:///migrations",
"postgres", driver)
m.Up() // or m.Step(2) if you want to explicitly set the number of migrations to run
}
```
### Litestream replication
## Getting started
Litestream is _not a necessary component_ to run the `./cmd/themis-server`
entrypoint and can be safely ignored when developing locally. Still, if you wish
to try it out, you can find the Litestream commands used in production in the
[start.sh](/start.sh) script. As per the Litestream docs, it should work fine
with [Minio](https://min.io/) but I have not tested it yet nor are there any
scripts provided to run it (yet).
Go to [getting started](GETTING_STARTED.md)
## SQLite
## Tutorials
### Importing From CSV
* [CockroachDB](database/cockroachdb/TUTORIAL.md)
* [PostgreSQL](database/postgres/TUTORIAL.md)
This is a neat feature built-in to SQLite. Using the source file at
[data/eu4-provinces.csv](/data/eu4-provinces.csv) you can import the data
directly into a SQLite database using the following command:
(more tutorials to come)
## Migration files
Each migration has an up and down migration. [Why?](FAQ.md#why-two-separate-files-up-and-down-for-a-migration)
```bash
$ sqlite3
# ...
sqlite> .mode csv
sqlite> .import data/eu4-provinces.csv provinces
sqlite> .schema provinces
CREATE TABLE provinces(
"ID" TEXT,
"Name" TEXT,
"Development" TEXT,
"BT" TEXT,
"BP" TEXT,
"BM" TEXT,
"Trade good" TEXT,
"Trade node" TEXT,
"Modifiers" TEXT,
"Type" TEXT,
"Continent" TEXT,
"Superregion" TEXT,
"Region" TEXT,
"Area" TEXT
);
sqlite> select count(1) from provinces;
3925
1481574547_create_users_table.up.sql
1481574547_create_users_table.down.sql
```
### Creating an SQL Dump From Imported Data
[Best practices: How to write migrations.](MIGRATIONS.md)
The init script at [migrations/init.sql](/migrations/init.sql) was initially
created after importing the CSV data and running the following commands:
## Versions
```bash
# In the same SQlite session as last section
sqlite> .output dump.sql
sqlite> .dump
```
Version | Supported? | Import | Notes
--------|------------|--------|------
**master** | :white_check_mark: | `import "github.com/golang-migrate/migrate/v4"` | New features and bug fixes arrive here first |
**v4** | :white_check_mark: | `import "github.com/golang-migrate/migrate/v4"` | Used for stable releases |
**v3** | :x: | `import "github.com/golang-migrate/migrate"` (with package manager) or `import "gopkg.in/golang-migrate/migrate.v3"` (not recommended) | **DO NOT USE** - No longer supported |
Note: The column names were _edited manually_ to remove capital letters and
spaces to make it easier to work with.
## Development and Contributing
### Claims Schema
Yes, please! [`Makefile`](Makefile) is your friend,
read the [development guide](CONTRIBUTING.md).
```sql
CREATE TABLE claim_types (
claim_type TEXT PRIMARY KEY
);
Also have a look at the [FAQ](FAQ.md).
CREATE TABLE claims (
id INTEGER PRIMARY KEY AUTOINCREMENT,
player TEXT,
claim_type TEXT,
val TEXT,
FOREIGN KEY(claim_type) REFERENCES claim_types(claim_type)
);
```
---
Looking for alternatives? [https://awesome-go.com/#database](https://awesome-go.com/#database).

@ -0,0 +1 @@
package themis

@ -75,11 +75,14 @@ func main() {
log.Info().Str("app_id", appId).Str("guild_id", guildId).Msg("connected to discord")
commands := []*discordgo.ApplicationCommand{
// Server info commands
{
Name: "info",
Description: "Server Information",
Type: discordgo.ChatApplicationCommand,
},
// EU4 claims commands
{
Name: "list-claims",
Description: "List current claims",

@ -4,6 +4,7 @@ go 1.19
require (
github.com/bwmarrin/discordgo v0.26.1
github.com/golang-migrate/migrate/v4 v4.16.2
github.com/mattn/go-sqlite3 v1.14.16
github.com/rs/zerolog v1.28.0
github.com/stretchr/testify v1.8.1
@ -12,10 +13,13 @@ require (
require (
github.com/davecgh/go-spew v1.1.1 // indirect
github.com/gorilla/websocket v1.4.2 // indirect
github.com/hashicorp/errwrap v1.1.0 // indirect
github.com/hashicorp/go-multierror v1.1.1 // indirect
github.com/mattn/go-colorable v0.1.12 // indirect
github.com/mattn/go-isatty v0.0.14 // indirect
github.com/mattn/go-isatty v0.0.16 // indirect
github.com/pmezard/go-difflib v1.0.0 // indirect
golang.org/x/crypto v0.1.0 // indirect
golang.org/x/sys v0.1.0 // indirect
go.uber.org/atomic v1.7.0 // indirect
golang.org/x/crypto v0.7.0 // indirect
golang.org/x/sys v0.8.0 // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect
)

@ -5,12 +5,21 @@ github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSs
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/godbus/dbus/v5 v5.0.4/go.mod h1:xhWf0FNVPg57R7Z0UbKHbJfkEywrmjJnf7w5xrFpKfA=
github.com/golang-migrate/migrate/v4 v4.16.2 h1:8coYbMKUyInrFk1lfGfRovTLAW7PhWp8qQDT2iKfuoA=
github.com/golang-migrate/migrate/v4 v4.16.2/go.mod h1:pfcJX4nPHaVdc5nmdCikFBWtm+UBpiZjRNNsyBbp0/o=
github.com/gorilla/websocket v1.4.2 h1:+/TMaTYc4QFitKJxsQ7Yye35DkWvkdLcvGKqM+x0Ufc=
github.com/gorilla/websocket v1.4.2/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE=
github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4=
github.com/hashicorp/errwrap v1.1.0 h1:OxrOeh75EUXMY8TBjag2fzXGZ40LB6IKw45YeGUDY2I=
github.com/hashicorp/errwrap v1.1.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4=
github.com/hashicorp/go-multierror v1.1.1 h1:H5DkEtf6CXdFp0N0Em5UCwQpXMWke8IA0+lD48awMYo=
github.com/hashicorp/go-multierror v1.1.1/go.mod h1:iw975J/qwKPdAO1clOe2L8331t/9/fmwbPZ6JB6eMoM=
github.com/lib/pq v1.10.2 h1:AqzbZs4ZoCBp+GtejcpCpcxM3zlSMx29dXbUSeVtJb8=
github.com/mattn/go-colorable v0.1.12 h1:jF+Du6AlPIjs2BiUiQlKOX0rt3SujHxPnksPKZbaA40=
github.com/mattn/go-colorable v0.1.12/go.mod h1:u5H1YNBxpqRaxsYJYSkiCWKzEfiAb1Gb520KVy5xxl4=
github.com/mattn/go-isatty v0.0.14 h1:yVuAays6BHfxijgZPzw+3Zlu5yQgKGP2/hcQbHb7S9Y=
github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94=
github.com/mattn/go-isatty v0.0.16 h1:bq3VjFmv/sOjHtdEhmkEV4x1AJtvUvOJ2PFAZ5+peKQ=
github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM=
github.com/mattn/go-sqlite3 v1.14.16 h1:yOQRA0RpS5PFz/oikGwBEqvAWhWg5ufRz4ETLjwpU1Y=
github.com/mattn/go-sqlite3 v1.14.16/go.mod h1:2eHXhiwb8IkHr+BDWZGa96P6+rkvnG63S2DGjv9HUNg=
github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0=
@ -22,19 +31,23 @@ github.com/rs/zerolog v1.28.0/go.mod h1:NILgTygv/Uej1ra5XxGf82ZFSLk58MFGAUS2o6us
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw=
github.com/stretchr/objx v0.5.0/go.mod h1:Yh+to48EsGEfYuaHDzXPcE3xhTkx73EhmCGUpEOglKo=
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU=
github.com/stretchr/testify v1.8.1 h1:w7B6lhMri9wdJUVmEZPGGhZzrYTPvgJArz7wNPgYKsk=
github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o6fzry7u4=
go.uber.org/atomic v1.7.0 h1:ADUqmZGgLDDfbSL9ZmPxKTybcoEYHgpYfELNoN+7hsw=
go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
golang.org/x/crypto v0.0.0-20210421170649-83a5a9bb288b/go.mod h1:T9bdIzuCu7OtxOm1hfPfRQxPLYneinmdGuTeoZ9dtd4=
golang.org/x/crypto v0.1.0 h1:MDRAIl0xIo9Io2xV565hzXHw3zVseKrJKodhohM5CjU=
golang.org/x/crypto v0.1.0/go.mod h1:RecgLatLF4+eUMCP1PoPZQb+cVrJcOPbHkTkbkB9sbw=
golang.org/x/crypto v0.7.0 h1:AvwMYaRytfdeVt3u6mLaxYtErKYjxA2OXjJ1HHq6t3A=
golang.org/x/crypto v0.7.0/go.mod h1:pYwdfH91IfpZVANVyUOhSIPZaFoJGxTFbZhFTx+dXZU=
golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg=
golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs=
golang.org/x/sys v0.0.0-20210630005230-0f9fa26af87c/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20210927094055-39ccf1dd6fa6/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.1.0 h1:kunALQeHf1/185U1i0GOB/fy1IPRDDpuoOOqRReG57U=
golang.org/x/sys v0.1.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220811171246-fbc7d0a398ab/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.8.0 h1:EBmGv8NaZBZTWvrbjNoL6HVt+IVy3QDQpJs7VRIw3tU=
golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=

@ -0,0 +1,3 @@
DROP TABLE claims;
DROP TABLE claim_types;
DROP TABLE provices;

@ -1,4 +1,3 @@
BEGIN TRANSACTION;
CREATE TABLE IF NOT EXISTS provinces(
"id" TEXT,
"name" TEXT,
@ -3967,5 +3966,3 @@ CREATE TABLE IF NOT EXISTS claims (
-- UNION select provinces.name from claims left join provinces on claims.val = provinces.area where claim_type = 'area'
-- );
-- END;
COMMIT;

@ -1,6 +0,0 @@
-- Part of #11
ALTER TABLE claims ADD COLUMN userid TEXT;
UPDATE claims SET userid='212714834490294273' WHERE player = 'shinemperor';
UPDATE claims SET userid='345340157333078016' WHERE player = 'wperron';
UPDATE claims SET userid='203896675960487936' WHERE player = 'Gillfren';
UPDATE claims SET userid='264861923814801408' WHERE player = 'B i r b';

@ -3,15 +3,20 @@ package themis
import (
"context"
"database/sql"
"embed"
_ "embed"
"errors"
"fmt"
"strings"
"github.com/golang-migrate/migrate/v4"
"github.com/golang-migrate/migrate/v4/database/sqlite3"
"github.com/golang-migrate/migrate/v4/source/iofs"
_ "github.com/mattn/go-sqlite3"
)
//go:embed migrations/init.sql
var initScript string
//go:embed migrations/*.sql
var migrations embed.FS
type Store struct {
db *sql.DB
@ -23,9 +28,24 @@ func NewStore(conn string) (*Store, error) {
return nil, fmt.Errorf("failed to open database: %w", err)
}
_, err = db.Exec(initScript)
d, err := iofs.New(migrations, "migrations")
if err != nil {
return nil, fmt.Errorf("failed to run init script: %w", err)
return nil, fmt.Errorf("failed to open iofs migration source: %w", err)
}
dr, err := sqlite3.WithInstance(db, &sqlite3.Config{})
if err != nil {
return nil, fmt.Errorf("failed to initialize sqlite3 migrate driver: %w", err)
}
m, err := migrate.NewWithInstance("iofs", d, "main", dr)
if err != nil {
return nil, fmt.Errorf("failed to initialize db migrate: %w", err)
}
err = m.Up()
if err != nil && !errors.Is(err, migrate.ErrNoChange) {
return nil, fmt.Errorf("failed to roll up migrations: %w", err)
}
return &Store{

@ -9,13 +9,14 @@ import (
_ "github.com/mattn/go-sqlite3"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
)
const TEST_CONN_STRING_PATTERN = "file:%s?mode=memory&cache=shared"
func TestStore_Claim(t *testing.T) {
store, err := NewStore(fmt.Sprintf(TEST_CONN_STRING_PATTERN, "TestStore_Claim"))
assert.NoError(t, err)
require.NoError(t, err)
type args struct {
player string

Loading…
Cancel
Save