store_interface.h 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414
  1. /** @file store_interface.h
  2. *
  3. * @brief Common store back end interfaces.
  4. *
  5. * Code using the store interface should include NOT this header, but rahter
  6. * `store.h`.
  7. *
  8. * This header is included by all back end implementations, which are in
  9. * their turn included by `store.h`.
  10. *
  11. * The basic interfaces for store and store iterator implementations are
  12. * defined here. New store implementations should include this header and
  13. * implement three basic elements:
  14. *
  15. * - A structure representing the store back end. This structure will be
  16. * opaque to all downstream code and its layout is entirely up to the
  17. * implementer.
  18. *
  19. * - A structure representing a store iterator state, also opaque.
  20. *
  21. * - The LSUP_StoreInt interface with all the functions defined in the
  22. * interface necessary to interact with the store.
  23. *
  24. * See the `store_htable.{c,h}` and `store_mdb.{c,h}` files for examples of
  25. * fully functioning implementations.
  26. *
  27. * The #LSUP_StoreInt structure defines a store interface for raw buffer
  28. * triples. Nothing in the store functions' signatures should hint at RDF
  29. * triples—they should accept and produce exclusively raw byte buffers
  30. * (#LSUP_Buffer). A store interface may have any of the `LSUP_STORE_*` faeture
  31. * flags which should be reflected in the way its members are implemented.
  32. */
  33. #ifndef _LSUP_STORE_INTERFACE_H
  34. #define _LSUP_STORE_INTERFACE_H
  35. #include "lsup/environment.h"
  36. /** @defgroup store_interface Store interface module
  37. * @ingroup private
  38. * @{
  39. */
  40. /*
  41. * Store feature flags.
  42. *
  43. * NOTE: LSUP_STORE_PERM need only be set by an implementation based on whether
  44. * the data may be cleared before the perogram ends. It is the client's
  45. * responsibility to guarantee permanence beyond the lifespan of the program. A
  46. * store featuring LSUP_STORE_PERM MUST guarantee that the data remain
  47. * available on storage for the user to further handle them.
  48. */
  49. typedef enum {
  50. LSUP_STORE_PERM = 1<<0, ///< Store is on a permanent support.
  51. LSUP_STORE_CTX = 1<<1, ///< Store supports contexts (quads).
  52. LSUP_STORE_IDX = 1<<2, ///< Store is fully SPO(C)-indexed.
  53. LSUP_STORE_TXN = 1<<3, ///< Supports transaction handling.
  54. LSUP_STORE_COW = 1<<4, ///< Copy on write. @sa #iter_next_fn_t()
  55. } LSUP_StoreFeature;
  56. /*
  57. * Store function types.
  58. */
  59. /** @brief Prototype: create any environment necessary for the store to work.
  60. *
  61. * #LSUP_store_new() calls this function before creating the store handle.
  62. *
  63. * This function should be idempotent on separate calls to the same `id`,
  64. * unless the `clear` option is set to `true`.
  65. *
  66. * @param[in,out] id Identifier to use for the store. This should be
  67. * a URI that uniquely identifies a back end for the implementation using it,
  68. * e.g. a SQL connection string, file path for an embedded store, the URL of a
  69. * REST API endpoint, etc. It may also be NULL, in which case it will be set to
  70. * the default identifier set by the implementation. It can be retrieved from
  71. * an existing store via #store_id_fn_t() .
  72. *
  73. * @param[in] clear Whether to remove an existing environment with the same ID.
  74. */
  75. typedef LSUP_rc (*store_setup_fn_t)(const char *id, bool clear);
  76. /** @brief Prototype: create a new store.
  77. *
  78. * @param[in] id Identifier for the new store. How this is interpreted, and
  79. * whether it is even used, depends on the implementation, which should
  80. * provide documentation on how to pass and interpret this parameter.
  81. *
  82. * @param[in] size Initial size for the store. It may be 0. Only meaningful
  83. * for stores that may preallocate memory, such as #HTStore.
  84. *
  85. * @return New store handle.
  86. */
  87. typedef void * (*store_new_fn_t)(const char *id, size_t size);
  88. /** @brief Prototype: free store handle.
  89. *
  90. * @param[in] store Store handle.
  91. *
  92. */
  93. typedef void (*store_free_fn_t)(void *store);
  94. /** @brief Prototype: get store size.
  95. *
  96. * @param[in] store The store to calculate size of.
  97. *
  98. * @return Number of stored SPO triples (across all contexts if supported).
  99. */
  100. typedef size_t (*store_size_fn_t)(const void *store);
  101. /** @brief Prototype: get the store ID.
  102. *
  103. * @param[in] store Store handle.
  104. *
  105. * @return store ID string. This is a copy and should be freed after use.
  106. */
  107. typedef char * (*store_id_fn_t)(const void *store);
  108. #if 0
  109. /** @brief Print stats about a store.
  110. *
  111. * TODO
  112. *
  113. * @param[in] store The store to get stats for.
  114. */
  115. typedef LSUP_rc (*store_stat_fn_t)(void *store, void *stat);
  116. #endif
  117. /** @brief Begin a transaction.
  118. *
  119. * Only for LSUP_STORE_TXN stores.
  120. *
  121. * The transaction handle is managed by the store implementation and can be any
  122. * data type.
  123. *
  124. * @param[in] store Store handle.
  125. *
  126. * @param[in] flags Transaction flags. These vary with each implementation.
  127. *
  128. * @param[out] txn Will point to the new open transaction on success, or to
  129. * undefined content on failure.
  130. *
  131. * @return LSUP_OK if the transaction started successfully, <0 on error.
  132. */
  133. typedef LSUP_rc (*store_txn_begin_fn_t)(void *store, int flags, void **txn);
  134. /** @brief Commit a transaction.
  135. *
  136. * Only for LSUP_STORE_TXN stores.
  137. *
  138. * @param[in] txn Transaction handle initialized by #store_txn_begin_fn_t().
  139. *
  140. * @return LSUP_OK if the transaction was committed successfully, <0 on error.
  141. */
  142. typedef LSUP_rc (*store_txn_commit_fn_t)(void *txn);
  143. /** @brief Abort a transaction.
  144. *
  145. * Only for LSUP_STORE_TXN stores.
  146. *
  147. * @param[in] txn Transaction handle initialized by #store_txn_begin_fn_t().
  148. */
  149. typedef void (*store_txn_abort_fn_t)(void *txn);
  150. /** @brief Update the context of triples in a context-aware store.
  151. *
  152. * Only defined in stores with the LSUP_STORE_CTX feature.
  153. *
  154. * @sa #LSUP_store_update_ctx_txn()
  155. */
  156. typedef LSUP_rc (*store_update_ctx_fn_t)(
  157. void *store, const LSUP_Buffer *old_c, const LSUP_Buffer *new_c,
  158. void *udata);
  159. /** @brief Initialize bulk triple load.
  160. *
  161. * @sa #LSUP_store_add_init_txn()
  162. */
  163. typedef void * (*store_add_init_fn_t)(
  164. void *store, const LSUP_Buffer *sc, void *udata);
  165. /** @brief Add one triple into the store.
  166. *
  167. * @sa LSUP_store_add_iter().
  168. */
  169. typedef LSUP_rc (*store_add_iter_fn_t)(
  170. void *it, const LSUP_BufferTriple * sspo);
  171. /** @brief Abort an add loop and free iterator.
  172. *
  173. * Only available for stores with the LSUP_STORE_CTX feature.
  174. *
  175. * @sa LSUP_store_add_abort().
  176. */
  177. typedef void (*store_add_abort_fn_t)(void *it);
  178. /** @brief Finalize an add loop and free iterator.
  179. *
  180. * @sa #LSUP_store_add_done().
  181. */
  182. typedef LSUP_rc (*store_add_done_fn_t)(void *it);
  183. /** @brief Add a single term to the store.
  184. *
  185. * @sa #LSUP_store_add_term_txn().
  186. */
  187. typedef LSUP_rc (*store_add_term_fn_t)(
  188. void *store, const LSUP_Buffer *sterm, void *udata);
  189. /*
  190. * Iterator function types.
  191. */
  192. /** @brief Prototype: look up triples by pattern matching.
  193. *
  194. * @sa #LSUP_store_lookup_txn().
  195. */
  196. typedef void * (*store_lookup_fn_t)(
  197. void *store,
  198. const LSUP_Buffer *ss, const LSUP_Buffer *sp, const LSUP_Buffer *so,
  199. const LSUP_Buffer *sc, void *udata, size_t *ct);
  200. /** @brief Prototype: check for existence of a triple (T/F).
  201. *
  202. * @note Unused interface function.
  203. *
  204. * @param[in] store Store to be queried.
  205. *
  206. * @param[in] sspo Triple to look up. All members must not be NULL.
  207. *
  208. * @param[in] sc Optional context to look into. It may be NULL. It is
  209. * disregarded by stores without the LSUP_STORE_CTX feature.
  210. *
  211. * @return Whether the triple exist in the store (/context).
  212. */
  213. typedef bool (*store_trp_exist_fn_t)(
  214. void *store, const LSUP_BufferTriple *sspo, const LSUP_Buffer *sc);
  215. /** @brief Prototype: yield the matching triples and advance the iterator.
  216. *
  217. * @sa LSUP_store_iter_next().
  218. */
  219. typedef LSUP_rc (*iter_next_fn_t)(
  220. void *it, LSUP_BufferTriple *sspo, LSUP_Buffer **ctx);
  221. /** @brief Prototype: free an iterator allocated by a lookup.
  222. *
  223. * @sa #LSUP_store_iter_free().
  224. */
  225. typedef void (*iter_free_fn_t)(void * it);
  226. /** @brief Prototype: get iterator active transaction handle.
  227. *
  228. * @sa #LSUP_store_iter_txn().
  229. */
  230. typedef void * (*iter_txn_fn_t)(void *it);
  231. /** @brief Prototype: delete triples by pattern matching.
  232. *
  233. * @sa #LSUP_store_remove_txn().
  234. */
  235. typedef LSUP_rc (*store_remove_fn_t)(
  236. void *store,
  237. const LSUP_Buffer *ss, const LSUP_Buffer *sp, const LSUP_Buffer *so,
  238. const LSUP_Buffer *sc, void *udata, size_t *ct);
  239. /** @brief Prototype: Get index of all graph (context) URIs in a store.
  240. *
  241. * @sa #LSUP_store_ctx_list_txn()
  242. */
  243. typedef LSUP_Buffer ** (*store_ctx_list_fn_t)(void *store, void *txn);
  244. /*
  245. * Iterface type definitions.
  246. */
  247. /** @brief Store interface.
  248. *
  249. * New store implementations should define a static structure with the relevant
  250. * members filled in. Some members are only relevant to certain types of stores
  251. * and may be set to NULL.
  252. *
  253. * #setup_fn may be optionally defined and MUST cause an idempotent action,
  254. * unless the `clear` argument is set to `true`. Callers should check if this
  255. * member is NULL and if it is not, call it at the beginning of the
  256. * interaction with the store.
  257. *
  258. * Transaction control members are only applicable to stores with the
  259. * #LSUP_STORE_TXN feature.
  260. */
  261. typedef struct store_if_t {
  262. // Basic properties.
  263. char name[16]; ///< Store type name.
  264. LSUP_StoreFeature features; ///< Feature flags.
  265. // Allocation, setup and deallocation.
  266. store_setup_fn_t setup_fn; ///< Called before #store_new_fn_t.
  267. store_new_fn_t new_fn; ///< Create a new store instance.
  268. store_free_fn_t free_fn; ///< Free the store.
  269. // Metadata.
  270. store_size_fn_t size_fn; ///< Number of triples in the store.
  271. store_id_fn_t id_fn; ///< Get store ID.
  272. // Transaction control.
  273. store_txn_begin_fn_t txn_begin_fn; ///< Begin transaction.
  274. store_txn_commit_fn_t txn_commit_fn; ///< Commit transaction.
  275. store_txn_abort_fn_t txn_abort_fn; ///< Abort transaction.
  276. //Context setting.
  277. store_update_ctx_fn_t update_ctx_fn; ///< Update context URI.
  278. ///<
  279. ///< Only available in stores with
  280. ///< #LSUP_STORE_CTX feature. Optional.
  281. // Addition.
  282. store_add_init_fn_t add_init_fn; ///< Initialize add iteration.
  283. store_add_iter_fn_t add_iter_fn; ///< Add one triple.
  284. store_add_abort_fn_t add_abort_fn; ///< Abort (roll back) the add process.
  285. ///<
  286. ///< Only available in
  287. ///< stores with #LSUP_STORE_TXN
  288. ///< feature. Optional.
  289. store_add_done_fn_t add_done_fn; ///< Complete the add process.
  290. store_add_term_fn_t add_term_fn; ///< Add (index) a term to the store.
  291. ///<
  292. ///< Only available in stores with
  293. ///< #LSUP_STORE_IDX feature. Optional.
  294. // Look up.
  295. store_lookup_fn_t lookup_fn; ///< Look up triples by pattern. 
  296. //store_trp_exist_fn_t exist_fn; ///< Check if a triple exists.
  297. iter_next_fn_t lu_next_fn; ///< Advance the lookup iterator.
  298. iter_free_fn_t lu_free_fn; ///< Free the lookup iterator.
  299. iter_txn_fn_t iter_txn_fn; ///< Get iterator's transaction.
  300. // Removal.
  301. store_remove_fn_t remove_fn; ///< Remove triples by pattern.
  302. // Context.
  303. store_ctx_list_fn_t ctx_list_fn; ///< Get all context URIs in a store.
  304. ///<
  305. ///< Only applicable to stores with
  306. ///< LSUP_STORE_CTX feature.
  307. } LSUP_StoreInt;
  308. /*
  309. * Template for a new store and iterator implementation.
  310. * These should be placed in the .c file where the interface functions are
  311. * defined, and declared as `extern` in the related .h file.
  312. const LSUP_StoreInt my_store_int = {
  313. .name = "My Store", // Truncated to 15 chars.
  314. .features = LSUP_STORE_PERM | LSUP_STORE_IDX,
  315. .setup_fn = my_setup_fn,
  316. .new_fn = my_new_fn,
  317. .free_fn = my_free_fn,
  318. .size_fn = my_size_fn,
  319. .id_fn = my_id_fn,
  320. .txn_begin_fn = my_txn_begin_fn,
  321. .txn_commit_fn = my_txn_commit_fn,
  322. .txn_abort_fn = my_txn_abort_fn,
  323. .ctx_update_fn = my_ctx_update_fn,
  324. .add_init_fn = my_init_fn,
  325. .add_iter_fn = my_iter_fn,
  326. .add_abort_fn = my_add_abort_fn,
  327. .add_done_fn = my_add_done_fn,
  328. .add_term_fn = my_add_term_fn,
  329. .lookup_fn = my_lookup_fn,
  330. .lu_next_fn = my_iter_next_fn,
  331. .lu_free_fn = my_iter_free_fn,
  332. .iter_txn_fn = my_iter_txn_fn,
  333. .remove_fn = my_remove_fn,
  334. .ctx_list_fn = my_ctx_list_fn,
  335. };
  336. */
  337. /// @} END defgroup store_interface
  338. #endif /* _LSUP_STORE_INTERFACE_H */