diff options
| author | 2021-08-26 22:40:05 +0200 | |
|---|---|---|
| committer | 2021-08-26 22:40:56 +0200 | |
| commit | b7cdcce9b5946fd469591124da4b9d4712708a39 (patch) | |
| tree | f103cf39d1a6cbeb56894c8e1f1a2d04cfae1d04 /sqlite.zig | |
| parent | implement reading an integer column into an enum value directly (diff) | |
| download | zig-sqlite-b7cdcce9b5946fd469591124da4b9d4712708a39.tar.gz zig-sqlite-b7cdcce9b5946fd469591124da4b9d4712708a39.tar.xz zig-sqlite-b7cdcce9b5946fd469591124da4b9d4712708a39.zip | |
implement reading a text column into an enum value directly
oneAlloc/nextAlloc can allocate memory so are allowed to use text
backed enums.
Diffstat (limited to '')
| -rw-r--r-- | sqlite.zig | 39 |
1 files changed, 39 insertions, 0 deletions
| @@ -682,6 +682,21 @@ pub fn Iterator(comptime Type: type) type { | |||
| 682 | debug.assert(columns == 1); | 682 | debug.assert(columns == 1); |
| 683 | return try self.readPointer(Type, allocator, 0); | 683 | return try self.readPointer(Type, allocator, 0); |
| 684 | }, | 684 | }, |
| 685 | .Enum => |TI| { | ||
| 686 | debug.assert(columns == 1); | ||
| 687 | |||
| 688 | const innervalue = try self.readField(Type.BaseType, 0, .{ | ||
| 689 | .allocator = allocator, | ||
| 690 | }); | ||
| 691 | |||
| 692 | if (comptime std.meta.trait.isZigString(Type.BaseType)) { | ||
| 693 | return std.meta.stringToEnum(Type, innervalue) orelse unreachable; | ||
| 694 | } | ||
| 695 | if (@typeInfo(Type.BaseType) == .Int) { | ||
| 696 | return @intToEnum(Type, @intCast(TI.tag_type, innervalue)); | ||
| 697 | } | ||
| 698 | @compileError("enum column " ++ @typeName(Type) ++ " must have a BaseType of either string or int"); | ||
| 699 | }, | ||
| 685 | .Struct => { | 700 | .Struct => { |
| 686 | std.debug.assert(columns == TypeInfo.Struct.fields.len); | 701 | std.debug.assert(columns == TypeInfo.Struct.fields.len); |
| 687 | return try self.readStruct(.{ | 702 | return try self.readStruct(.{ |
| @@ -1711,6 +1726,30 @@ test "sqlite: read a single value into an enum backed by an integer" { | |||
| 1711 | } | 1726 | } |
| 1712 | } | 1727 | } |
| 1713 | 1728 | ||
| 1729 | test "sqlite: read a single value into an enum backed by a string" { | ||
| 1730 | var arena = std.heap.ArenaAllocator.init(testing.allocator); | ||
| 1731 | defer arena.deinit(); | ||
| 1732 | |||
| 1733 | var db = try getTestDb(); | ||
| 1734 | try createTestTables(&db); | ||
| 1735 | |||
| 1736 | try db.exec("INSERT INTO user(id, favorite_color) VALUES(?{usize}, ?{[]const u8})", .{}, .{ | ||
| 1737 | .id = @as(usize, 10), | ||
| 1738 | .age = @as([]const u8, "violet"), | ||
| 1739 | }); | ||
| 1740 | |||
| 1741 | const query = "SELECT favorite_color FROM user WHERE id = ?{usize}"; | ||
| 1742 | |||
| 1743 | var stmt: Statement(.{}, ParsedQuery.from(query)) = try db.prepare(query); | ||
| 1744 | defer stmt.deinit(); | ||
| 1745 | |||
| 1746 | const b = try stmt.oneAlloc(TestUser.Color, &arena.allocator, .{}, .{ | ||
| 1747 | .id = @as(usize, 10), | ||
| 1748 | }); | ||
| 1749 | try testing.expect(b != null); | ||
| 1750 | try testing.expectEqual(TestUser.Color.violet, b.?); | ||
| 1751 | } | ||
| 1752 | |||
| 1714 | test "sqlite: read a single value into void" { | 1753 | test "sqlite: read a single value into void" { |
| 1715 | var db = try getTestDb(); | 1754 | var db = try getTestDb(); |
| 1716 | try addTestData(&db); | 1755 | try addTestData(&db); |