Skip to content

Commit 09c3d40

Browse files
reset after execute (#13)
1 parent 5fb542a commit 09c3d40

File tree

5 files changed

+46
-10
lines changed

5 files changed

+46
-10
lines changed

Playgrounds/README.playground/Contents.swift

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ try database.execute(sql)
3939
Insert new contacts Paul and John.
4040
*/
4141
let insert = try database.prepare("INSERT INTO contacts (id, name) VALUES (?, ?);")
42-
try insert.bind(parameters: 1, "Paul").execute().reset()
42+
try insert.bind(parameters: 1, "Paul").execute()
4343
try insert.bind(parameters: 2, "John").execute()
4444
/*:
4545
## Select
@@ -48,19 +48,20 @@ try insert.bind(parameters: 2, "John").execute()
4848
*/
4949
struct Contact: Codable {
5050
let id: Int
51-
let name: String
51+
let name: String?
5252
}
5353

5454
let select = try database.prepare("SELECT * FROM contacts;")
5555
let contacts = try select.array(Contact.self)
56+
print(contacts)
5657
/*:
5758
## DataFrame
5859

5960
The [DataFrame](https://developer.apple.com/documentation/tabulardata/dataframe) from the [TabularData](https://developer.apple.com/documentation/tabulardata) framework is supported.
6061

6162
It can help to print the table.
6263
*/
63-
let df = try database.prepare("SELECT * FROM contacts;").dataFrame()
64+
let df = try select.dataFrame()
6465
print(df)
6566
/*:
6667
```

README.md

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ try database.execute(sql)
3838
Insert new contacts Paul and John.
3939
```swift
4040
let insert = try database.prepare("INSERT INTO contacts (id, name) VALUES (?, ?);")
41-
try insert.bind(parameters: 1, "Paul").execute().reset()
41+
try insert.bind(parameters: 1, "Paul").execute()
4242
try insert.bind(parameters: 2, "John").execute()
4343
```
4444
## Select
@@ -47,19 +47,20 @@ Select all contacts from database.
4747
```swift
4848
struct Contact: Codable {
4949
let id: Int
50-
let name: String
50+
let name: String?
5151
}
5252

5353
let select = try database.prepare("SELECT * FROM contacts;")
5454
let contacts = try select.array(Contact.self)
55+
print(contacts)
5556
```
5657
## DataFrame
5758

5859
The [DataFrame](https://developer.apple.com/documentation/tabulardata/dataframe) from the [TabularData](https://developer.apple.com/documentation/tabulardata) framework is supported.
5960

6061
It can help to print the table.
6162
```swift
62-
let df = try database.prepare("SELECT * FROM contacts;").dataFrame()
63+
let df = try select.dataFrame()
6364
print(df)
6465
```
6566
```

Sources/SQLyra/DataFrame.swift

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,7 @@ extension PreparedStatement {
4141
}
4242
var df = DataFrame(columns: columns)
4343
var count = 0
44+
defer { _reset() }
4445
while let row = try row() {
4546
df.appendEmptyRow()
4647
for index in (0..<columnCount) {

Sources/SQLyra/PreparedStatement.swift

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,8 @@ public final class PreparedStatement: DatabaseHandle {
3333
/// - Throws: ``DatabaseError``
3434
@discardableResult
3535
public func execute() throws -> PreparedStatement {
36-
try check(sqlite3_step(stmt), SQLITE_DONE)
36+
defer { _reset() }
37+
return try check(sqlite3_step(stmt), SQLITE_DONE)
3738
}
3839

3940
/// Reset the prepared statement.
@@ -47,6 +48,11 @@ public final class PreparedStatement: DatabaseHandle {
4748
public func reset() throws -> PreparedStatement {
4849
try check(sqlite3_reset(stmt))
4950
}
51+
52+
/// clear error state and prepare for reuse
53+
func _reset() {
54+
sqlite3_reset(stmt)
55+
}
5056
}
5157

5258
// MARK: - Retrieving Statement SQL
@@ -176,6 +182,7 @@ extension PreparedStatement {
176182
}
177183

178184
public func array<T>(_ type: T.Type, using decoder: RowDecoder) throws -> [T] where T: Decodable {
185+
defer { _reset() }
179186
var array: [T] = []
180187
while let row = try row() {
181188
let value = try row.decode(type, using: decoder)

Tests/SQLyraTests/PreparedStatementTests.swift

Lines changed: 29 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ struct Contact: Codable, Equatable, Sendable {
88
let rating: Double?
99
let image: Data?
1010

11-
static let table = "CREATE TABLE contacts (id INT, name TEXT, rating FLOAT, image BLOB);"
11+
static let table = "CREATE TABLE contacts (id INT, name TEXT, rating REAL, image BLOB) STRICT;"
1212
static let insert = "INSERT INTO contacts (id, name, rating, image) VALUES (:id, :name, :rating, :image)"
1313
}
1414

@@ -71,7 +71,7 @@ struct PreparedStatementTests {
7171
@Test func columns() throws {
7272
let insert = try db.prepare(Contact.insert)
7373

74-
try insert.bind(parameters: 5, "A", 2.0, .null).execute().reset()
74+
try insert.bind(parameters: 5, "A", 2.0, .null).execute()
7575
try insert.bind(parameters: 6, "B", .null, .blob(Data("123".utf8))).execute()
7676

7777
let select = try db.prepare("SELECT * FROM contacts;")
@@ -94,11 +94,37 @@ struct PreparedStatementTests {
9494
#expect(contracts == expected)
9595
}
9696

97+
@Test func decode() throws {
98+
let insert = try db.prepare(Contact.insert)
99+
100+
try insert.bind(parameters: 5, "A", 2.0, .null).execute()
101+
try insert.bind(parameters: 6, "B", .null, .blob(Data("123".utf8))).execute()
102+
103+
let select = try db.prepare("SELECT * FROM contacts;")
104+
let contracts = try select.array(Contact.self)
105+
106+
let expected = [
107+
Contact(id: 5, name: "A", rating: 2.0, image: nil),
108+
Contact(id: 6, name: "B", rating: nil, image: Data("123".utf8)),
109+
]
110+
#expect(contracts == expected)
111+
}
112+
113+
@Test func execute() throws {
114+
let insert = try db.prepare(Contact.insert)
115+
116+
try insert.bind(name: ":id", parameter: "invalid")
117+
#expect(throws: DatabaseError.self) { try insert.execute() }
118+
119+
try insert.bind(name: ":id", parameter: 4)
120+
#expect(throws: Never.self) { try insert.execute() }
121+
}
122+
97123
@available(macOS 12, iOS 15, tvOS 15, watchOS 8, *)
98124
@Test func dataFrame() throws {
99125
let insert = try db.prepare(Contact.insert)
100126

101-
try insert.bind(parameters: 5, "A").execute().reset()
127+
try insert.bind(parameters: 5, "A").execute()
102128
try insert.bind(parameters: 6, "B").execute()
103129

104130
let df = try db.prepare("SELECT * FROM contacts;").dataFrame()

0 commit comments

Comments
 (0)