(** Persistent key-value store interface for OCaml.
    This is a virtual library defining a unified frontend for a number of
    key-value storage implementations. Implementations of the following backends
    currently exist: SQLite, DBM, PostgreSQL.
    You can choose the backend you prefer by installing packages
    [ocsipersist-sqlite], [ocsipersist-dbm] or [ocsipersist-pgsql].
    
    Library [Ocsipersist_settings], provided by each of the backends,
    contain the configuration options for your stores.

    Packages [ocsipersist-sqlite-config], [ocsipersist-dbm-config] and
    [ocsipersist-pgsql-config] add the possibility to configure the
    corresponding backends from Ocsigen Server's configuration file. 

    Ocsipersist is used by Eliom for persistent session storages and references.

    Ocsipersist defines several interfaces:
    - [Ref] is the simpler the use: it provides persistent references
    - [Store] is a lower level interface for persistent values
    - [Polymorphic] is a polymorphic table, using Mahshal
    - [Functorial] is a typed interface for your own data type

Example of use from the toplevel:

{[
# #require "lwt_ppx";;
(* #thread;; if you are using OCaml < 5.0.0 *)
# #require "ocsipersist-sqlite";;
# Ocsipersist.init ();;
# let r = Ocsipersist.Ref.ref ~persistent:"r" 444;;
val r : int Ocsipersist.Ref.t = <abstr>
# Lwt_main.run (let%lwt v = Ocsipersist.Ref.get r in print_int v; Lwt.return_unit);;
444- : unit = ()
]}
*)

module Functorial : Ocsipersist_lib.Sigs.FUNCTORIAL
(** Functorial frontent. Allows for custom (de)serialisation functions, which
    keeps data human-readable in the backend. *)

module type TABLE = Ocsipersist_lib.Sigs.TABLE
(** Table representation as generated by the functor {!Functorial.Table} *)

module Polymorphic : Ocsipersist_lib.Sigs.POLYMORPHIC
(** Polymorphic frontent. Relies on {!Marshal} for (de)serialisation, which
    means that data will be stored in the backend in a fashion that is not
    necessarily easily readable by non-OCaml-based life forms. If this is an
    issue for you, you can rely on the functorial frontend instead. *)

type 'value table = 'value Polymorphic.table
(** Table representation as generated by the function {!Polymorphic.open_table} *)

module Ref : Ocsipersist_lib.Sigs.REF
(** Simple interface for persistent references.
    Relies on {!Stdlib.Marshal} for (de)serialisation, which entails
    the same limitations as for the {!Polymorphic} frontend. If this is an
    issue you can rely on {!Functorial} frontend instead (see {!TABLE.Variable}). *)

module Store : Ocsipersist_lib.Sigs.STORE
(** The variable store allows for the persistent storage of individual
    variables. Relies on {!Stdlib.Marshal} for (de)serialisation, which entails
    the same limitations as for the {!Polymorphic} frontend. If this is an
    issue you can rely on {!Functorial} frontend instead (see {!TABLE.Variable}). *)

type store = Store.store
type 'a variable = 'a Store.t

module Ref_json : Ocsipersist_lib.Sigs.REF_JSON
(** Type-safe persistent references using {!Deriving_Json} for
    serialisation. Unlike {!Ref}, this does not rely on {!Stdlib.Marshal}
    and is safe across OCaml versions. Requires types annotated with
    [\[@@deriving json\]] (from [js_of_ocaml-ppx_deriving_json]). *)

module Store_json : Ocsipersist_lib.Sigs.STORE_JSON
(** Type-safe variable store using {!Deriving_Json} for serialisation.
    Unlike {!Store}, this does not rely on {!Stdlib.Marshal}
    and is safe across OCaml versions. Requires types annotated with
    [\[@@deriving json\]] (from [js_of_ocaml-ppx_deriving_json]).

    Note: The dependency on [js_of_ocaml] is only for the {!Deriving_Json}
    runtime library, which provides type-safe JSON serialisation. This is
    the same serialisation mechanism used by Eliom for client-server
    communication. No JavaScript compilation is involved. *)

val init : unit -> unit
