1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153
|
go-cowsql [](https://github.com/cowsql/go-cowsql/actions/workflows/build-and-test.yml) [](https://coveralls.io/github/cowsql/go-cowsql?branch=main) [](https://goreportcard.com/report/github.com/cowsql/go-cowsql) [](https://godoc.org/github.com/cowsql/go-cowsql)
======
This repository provides the `go-cowsql` Go package, containing bindings for the
[cowsql](https://github.com/cowsql/cowsql) C library and a pure-Go
client for the cowsql wire [protocol](https://github.com/cowsql/cowsql/blob/main/doc/protocol.md).
Fork of Canonical go-dqlite
---------------------------
These bindings are a cowsql-oriented fork of Canonical's
[go-dqlite](https://github.com/canonical/go-dqlite) ones, which were originally
written by cowsql's author
[himself](https://github.com/canonical/go-dqlite/commits?author=freeekanayaka)
while working at Canonical.
Usage
-----
The best way to understand how to use the ```go-cowsql``` package is probably by
looking at the source code of the [demo
program](https://github.com/cowsql/go-cowsql/blob/main/cmd/cowsql-demo/cowsql-demo.go) and
use it as example.
In general your application will use code such as:
```go
dir := "/path/to/data/directory"
address := "1.2.3.4:666" // Unique node address
cluster := []string{...} // Optional list of existing nodes, when starting a new node
app, err := app.New(dir, app.WithAddress(address), app.WithCluster(cluster))
if err != nil {
// ...
}
db, err := app.Open(context.Background(), "my-database")
if err != nil {
// ...
}
// db is a *sql.DB object
if _, err := db.Exec("CREATE TABLE my_table (n INT)"); err != nil
// ...
}
```
Build
-----
In order to use the go-cowsql package in your application, you'll need to have
the [cowsql](https://github.com/cowsql/cowsql) C library installed on your
system, along with its dependencies.
By default, go-cowsql's `client` module supports storing a cache of the
cluster's state in a SQLite database, locally on each cluster member. (This is
not to be confused with any SQLite databases that are managed by cowsql.) In
order to do this, it imports https://github.com/mattn/go-sqlite3, and so you
can use the `libsqlite3` build tag to control whether go-sqlite3 links to a
system libsqlite3 or builds its own. You can also disable support for SQLite
node stores entirely with the `nosqlite3` build tag (unique to go-cowsql). If
you pass this tag, your application will not link *directly* to libsqlite3 (but
it will still link it *indirectly* via libcowsql, unless you've dropped the
sqlite3.c amalgamation into the cowsql build).
Documentation
-------------
The documentation for this package can be found on [pkg.go.dev](https://pkg.go.dev/github.com/cowsql/go-cowsql).
Demo
----
To see cowsql in action, either install the Debian package from the PPA:
```bash
sudo add-apt-repository -y ppa:cowsql/master
sudo apt install cowsql libcowsql-dev
```
or build the cowsql C library and its dependencies from source, as described
[here](https://github.com/cowsql/cowsql#build), and then run:
```
go install -tags libsqlite3 ./cmd/cowsql-demo
```
from the top-level directory of this repository.
This builds a demo cowsql application, which exposes a simple key/value store
over an HTTP API.
Once the `cowsql-demo` binary is installed (normally under `~/go/bin` or
`/usr/bin/`), start three nodes of the demo application:
```bash
cowsql-demo --api 127.0.0.1:8001 --db 127.0.0.1:9001 &
cowsql-demo --api 127.0.0.1:8002 --db 127.0.0.1:9002 --join 127.0.0.1:9001 &
cowsql-demo --api 127.0.0.1:8003 --db 127.0.0.1:9003 --join 127.0.0.1:9001 &
```
The `--api` flag tells the demo program where to expose its HTTP API.
The `--db` flag tells the demo program to use the given address for internal
database replication.
The `--join` flag is optional and should be used only for additional nodes after
the first one. It informs them about the existing cluster, so they can
automatically join it.
Now we can start using the cluster. Let's insert a key pair:
```bash
curl -X PUT -d my-value http://127.0.0.1:8001/my-key
```
and then retrieve it from the database:
```bash
curl http://127.0.0.1:8001/my-key
```
Currently the first node is the leader. If we stop it and then try to query the
key again curl will fail, but we can simply change the endpoint to another node
and things will work since an automatic failover has taken place:
```bash
kill -TERM %1; curl http://127.0.0.1:8002/my-key
```
Shell
------
A basic SQLite-like cowsql shell is available in the `cowsql-tools` package or
can be built with:
```
go install -tags libsqlite3 ./cmd/cowsql
```
```
Usage:
cowsql -s <servers> <database> [command] [flags]
```
Example usage in the case of the `cowsql-demo` example listed above:
```
cowsql -s 127.0.0.1:9001 demo
cowsql> SELECT * FROM model;
my-key|my-value
```
The shell supports normal SQL queries plus the special `.cluster` and `.leader`
commands to inspect the cluster members and the current leader.
|