summaryrefslogtreecommitdiff
path: root/README.md
diff options
context:
space:
mode:
Diffstat (limited to 'README.md')
-rw-r--r--README.md122
1 files changed, 122 insertions, 0 deletions
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..658498e
--- /dev/null
+++ b/README.md
@@ -0,0 +1,122 @@
1# zig-sqlite
2
3This package is a thin wrapper around [sqlite](https://sqlite.org/index.html)'s C API.
4
5## Requirements
6
7* Linux
8* the system and development package for sqlite
9 * `libsqlite3-dev` for Debian and derivatives
10 * `sqlite3-devel` for Fedora
11
12## Installation
13
14Since there's no package manager for Zig yet, the recommended way is to use a git submodule:
15
16 $ git submodule add https://git.sr.ht/~vrischmann/zig-sqlite src/sqlite
17
18Then add the following to your `build.zig` target(s):
19
20 exe.linkLibC();
21 exe.linkSystemLibrary("sqlite3");
22 exe.addPackage(.{ .name = "sqlite", .path = "src/sqlite/sqlite.zig" });
23
24Now you should be able to import sqlite like this:
25
26 const sqlite = @import("sqlite");
27
28## Usage
29
30### Initialization
31
32You must create and initialize an instance of `sqlite.Db`:
33
34 var db: sqlite.Db = undefined;
35 try db.init(allocator, .{ .mode = sqlite.Db.Mode{ .File = "/home/vincent/mydata.db" } });
36
37The `init` method takes an allocator and an optional tuple which will used to configure sqlite.
38
39Right now the only member used in that tuple is `mode` which defines if the sqlite database is in memory or uses a file.
40
41### Preparing a statement
42
43sqlite works exclusively by using prepared statements. The wrapper type is `sqlite.Statement`. Here is how you get one:
44
45 const query =
46 \\SELECT id, name, age, salary FROM employees WHERE age > ? AND age < ?
47 ;
48
49 var stmt = try db.prepare(query, .{
50 .age1 = 20,
51 .age2 = 40,
52 });
53 defer stmt.deinit();
54
55The `Db.prepare` method takes a `comptime` query string and a tuple of bind parameters.
56
57The number of bind parameters is comptime checked against the number of bind markers in the query string, so if you have 2 bind markers
58you must provide 2 bind parameters.
59
60Note that the fields name is irrelevant, only their order is relevant.
61
62See the section "Bind parameters and resultset rows" for more information on the types mapping rules.
63
64### Executing a statement
65
66For queries which do not return data (`INSERT`, `UPDATE`) you can use the `exec` method:
67
68 const query =
69 \\UPDATE foo SET salary = ? WHERE id = ?
70 ;
71
72 var stmt = try db.prepare(query, .{
73 .salary = 20000,
74 .id = 40,
75 });
76 defer stmt.deinit();
77
78 try stmt.exec();
79
80### Reading data
81
82For queries which do return data you can use the `all` method:
83
84 const query =
85 \\SELECT id, name, age, salary FROM employees WHERE age > ? AND age < ?
86 ;
87
88 var stmt = try db.prepare(query, .{
89 .age1 = 20,
90 .age2 = 40,
91 });
92 defer stmt.deinit();
93
94 const rows = try stmt.all(
95 struct {
96 id: usize,
97 name: []const u8,
98 age: u16,
99 salary: u32,
100 },
101 .{ .allocator = allocator },
102 );
103 for (rows) |row| {
104 std.log.debug("id: {} ; name: {}; age: {}; salary: {}", .{ row.id, row.name, row.age, row.salary });
105 }
106
107The `all` method takes a type and an optional tuple.
108
109The type represents a "row", it can be:
110* a struct where each field maps to the corresponding column in the resultset (so field 0 must map to field 1 and so on).
111* a single type, in that case the resultset must only return one column.
112
113Not all types are allowed, see the section "Bind parameters and resultset rows" for more information on the types mapping rules.
114
115### Bind parameters and resultset rows
116
117Since sqlite doesn't have many [types](https://www.sqlite.org/datatype3.html) only a small number of Zig types are allowed in binding parameters and in resultset mapping types.
118
119Here are the rules for bind parameters:
120* any Zig `Int` or `ComptimeInt` is tread as a `INTEGER`.
121* any Zig `Float` or `ComptimeFloat` is treated as a `REAL`.
122* `[]const u8`, `[]u8` or any array of `u8` is treated as a `TEXT` or `BLOB`.