@ -17,33 +17,53 @@ module type Table = sig
val table : string
end
module type Blob = sig
module type Blob Internal = sig
module Table : Table
val blob_of_key : Table . key -> Sqlite3 . Data . t
type key_blob = Sqlite3 . Data . t
val blob_of_value : Table . value -> Sqlite3 . Data . t
type value_blob = Sqlite3 . Data . t
val key_of_blob : Sqlite3 . Data . t -> Table . key option
val blob_of_key : Table . key -> key_blob
val value_of_blob : Sqlite3 . Data . t -> Table . value option
val blob_of_value : Table . value -> value_blob
val value_of_blob : value_blob -> Table . value option
end
module type S = sig
include Blob
module Table : Table
type key_blob
type value_blob
val blob_of_key : Table . key -> key_blob
val blob_of_value : Table . value -> value_blob
external key_blob_of_data : Sqlite3 . Data . t -> key_blob = " %identity "
val replace : Table . key -> Table . value -> unit
external value_blob_of_data : Sqlite3 . Data . t -> value_blob = " %identity "
val find : Table . key -> Table . value option
val value_of_blob : value_blob -> Table . value option
val delete : Table . key -> unit
val replace : key_blob -> value_blob -> unit
val find : key_blob -> Table . value option
val delete : key_blob -> unit
end
(* The functor is mostly here to provide a modicum of type safety around blobing/unblobing *)
module Make ( Table : Table ) : S with module Table = Table = struct
module Unsafe : Blob with module Table = Table = struct
module Unsafe : Blob Internal with module Table = Table = struct
module Table = Table
type key_blob = Sqlite3 . Data . t
type value_blob = Sqlite3 . Data . t
let blob x = Sqlite3 . Data . BLOB ( Marshal . to_string x [] )
let unblob = function
@ -58,14 +78,16 @@ module Make (Table : Table) : S with module Table = Table = struct
let blob_of_value = blob
let key_of_blob = unblob
let value_of_blob = unblob
end
(* cannot mix, e.g., blob_key and blob_value now *)
include Unsafe
external key_blob_of_data : Sqlite3 . Data . t -> key_blob = " %identity "
external value_blob_of_data : Sqlite3 . Data . t -> value_blob = " %identity "
let register_statement stmt_fmt =
let k stmt0 =
let stmt_ref = ref None in
@ -91,28 +113,25 @@ module Make (Table : Table) : S with module Table = Table = struct
let get_replace_statement =
register_statement " REPLACE INTO %s(key, value) VALUES(:k, :v) " Table . table
let replace key value =
let replace key _blob value_blob =
let replace_stmt = get_replace_statement () in
Sqlite3 . bind replace_stmt 1 ( blob_of_key key )
| > SqliteUtils . check_sqlite_error ~ log : " replace bind key " ;
Sqlite3 . bind replace_stmt 2 ( blob_of_value value )
Sqlite3 . bind replace_stmt 1 key_blob | > SqliteUtils . check_sqlite_error ~ log : " replace bind key " ;
Sqlite3 . bind replace_stmt 2 value_blob
| > SqliteUtils . check_sqlite_error ~ log : " replace bind value " ;
SqliteUtils . sqlite_unit_step ~ finalize : false ~ log : " KeyValue.replace " replace_stmt
let get_select_statement = register_statement " SELECT value FROM %s WHERE key = :k " Table . table
let find key =
let find key _blob =
let select_stmt = get_select_statement () in
Sqlite3 . bind select_stmt 1 ( blob_of_key key )
| > SqliteUtils . check_sqlite_error ~ log : " insert bind key " ;
Sqlite3 . bind select_stmt 1 key_blob | > SqliteUtils . check_sqlite_error ~ log : " insert bind key " ;
SqliteUtils . sqlite_result_step ~ finalize : false ~ log : " KeyValue.find " select_stmt
| > Option . bind ~ f : value_of_blob
let get_delete_statement = register_statement " DELETE FROM %s WHERE key = :k " Table . table
let delete key =
let delete key _blob =
let delete_stmt = get_delete_statement () in
Sqlite3 . bind delete_stmt 1 ( blob_of_key key )
| > SqliteUtils . check_sqlite_error ~ log : " delete bind key " ;
Sqlite3 . bind delete_stmt 1 key_blob | > SqliteUtils . check_sqlite_error ~ log : " delete bind key " ;
SqliteUtils . sqlite_unit_step ~ finalize : false ~ log : " KeyValue.delete " delete_stmt
end