|
| 1 | +#include "ansi-codes/ansi-codes.h" |
| 2 | +#include "bytes/bytes.h" |
| 3 | +#include "c_fsio/include/fsio.h" |
| 4 | +#include "c_greatest/greatest/greatest.h" |
| 5 | +#include "c_string_buffer/include/stringbuffer.h" |
| 6 | +#include "c_stringfn/include/stringfn.h" |
| 7 | +#include "c_vector/vector/vector.h" |
| 8 | +#include "iowow-compound-test/iowow-compound-test.h" |
| 9 | +#include "log/log.h" |
| 10 | +#include "ms/ms.h" |
| 11 | +#include "timestamp/timestamp.h" |
| 12 | +#include <iowow/iwkv.h> |
| 13 | + |
| 14 | +TEST t_iowow_compound_test2(){ |
| 15 | + PASS(); |
| 16 | +} |
| 17 | + |
| 18 | +/// Compound keys demo. |
| 19 | +/// |
| 20 | +/// Compound keys allows associate one `key value` with many references |
| 21 | +/// represented as VNUM64 (eg.: Non unique table indexes). |
| 22 | +/// |
| 23 | +/// Compound mainly used for non-unique indexes in ejdb2 database engine: |
| 24 | +/// |
| 25 | +/// `<prefix key value>.<document id>` |
| 26 | +TEST t_iowow_compound_test1(){ |
| 27 | + struct user_s { |
| 28 | + uint32_t id; |
| 29 | + char *name; |
| 30 | + }; |
| 31 | + |
| 32 | + struct chat_root_s { |
| 33 | + char *name; |
| 34 | + struct user_s users[5]; |
| 35 | + }; |
| 36 | + |
| 37 | + static struct chat_root_s rooms[] = { |
| 38 | + { |
| 39 | + .name = "Meeting room", |
| 40 | + .users ={ |
| 41 | + { .id = 1, .name = "Joy Lynn" }, |
| 42 | + { .id = 2, .name = "Aubrey Sparks" }, |
| 43 | + { .id = 3, .name = "Vinnie Kaye" }, |
| 44 | + { 0 } |
| 45 | + } |
| 46 | + }, |
| 47 | + { |
| 48 | + .name = "Webinar room", |
| 49 | + .users ={ |
| 50 | + { .id = 4, .name = "Arda Payne" }, |
| 51 | + { .id = 2, .name = "Joy Lynn" }, |
| 52 | + { 0 } |
| 53 | + } |
| 54 | + } |
| 55 | + }; |
| 56 | + |
| 57 | + IWKV_OPTS opts = { |
| 58 | + .path = "compoundkeys.db", |
| 59 | + .oflags = IWKV_TRUNC |
| 60 | + }; |
| 61 | + IWKV iwkv; |
| 62 | + IWDB db; |
| 63 | + IWKV_cursor cur = 0; |
| 64 | + iwrc rc = iwkv_open(&opts, &iwkv); |
| 65 | + |
| 66 | + RCRET(rc); |
| 67 | + |
| 68 | + rc = iwkv_db(iwkv, 1, IWDB_COMPOUND_KEYS, &db); |
| 69 | + RCGO(rc, finish); |
| 70 | + |
| 71 | + // Persist all rooms with members |
| 72 | + for (int i = 0; i < sizeof(rooms) / sizeof(rooms[0]); ++i) { |
| 73 | + int j = 0; |
| 74 | + struct chat_root_s *room = &rooms[i]; |
| 75 | + for (struct user_s *user = &room->users[0]; user->id; user = &room->users[++j]) { |
| 76 | + IWKV_val key = { .data = room->name, .size = strlen(room->name), .compound = user->id }; |
| 77 | + IWKV_val val = { .data = user->name, .size = strlen(user->name) }; |
| 78 | + RCC(rc, finish, iwkv_put(db, &key, &val, 0)); |
| 79 | + } |
| 80 | + } |
| 81 | + |
| 82 | + // Get specific user from the room |
| 83 | + { |
| 84 | + IWKV_val key = { .data = "Webinar room", .size = sizeof("Webinar room") - 1, .compound = 2 }; |
| 85 | + IWKV_val val; |
| 86 | + RCC(rc, finish, iwkv_get(db, &key, &val)); |
| 87 | + fprintf(stdout, "\n>>>> Found: '%.*s' in room '%s' by id: %d\n", |
| 88 | + (int)val.size, (char *)val.data, |
| 89 | + (char *)key.data, (int)key.compound); |
| 90 | + iwkv_val_dispose(&val); |
| 91 | + } |
| 92 | + |
| 93 | + // Iterate over all members in `Meeting room` |
| 94 | + { |
| 95 | + size_t len = strlen(rooms[0].name); |
| 96 | + fprintf(stdout, "\n>>>> Iterate over all members in %s\n", rooms[0].name); |
| 97 | + IWKV_val val, key = { .data = rooms[0].name, .size = len }; |
| 98 | + RCC(rc, finish, iwkv_cursor_open(db, &cur, IWKV_CURSOR_GE, &key)); |
| 99 | + do { |
| 100 | + RCC(rc, finish, iwkv_cursor_get(cur, &key, &val)); |
| 101 | + if (memcmp(key.data, rooms[0].name, MIN(key.size, len))) { |
| 102 | + // We rolled to end of `Meeting room` room |
| 103 | + iwkv_kv_dispose(&key, &val); |
| 104 | + break; |
| 105 | + } |
| 106 | + fprintf(stdout, "%.*s: %d %.*s\n", |
| 107 | + (int)key.size, (char *)key.data, |
| 108 | + (int)key.compound, |
| 109 | + (int)val.size, |
| 110 | + (char *)val.data); |
| 111 | + iwkv_kv_dispose(&key, &val); |
| 112 | + } while ((rc = iwkv_cursor_to(cur, IWKV_CURSOR_PREV)) == 0); |
| 113 | + rc = 0; |
| 114 | + } |
| 115 | + |
| 116 | +finish: |
| 117 | + if (cur) { |
| 118 | + iwkv_cursor_close(&cur); |
| 119 | + } |
| 120 | + iwkv_close(&iwkv); |
| 121 | + |
| 122 | + PASS(); |
| 123 | +} /* t_iowow_compound_test1 */ |
| 124 | + |
| 125 | +SUITE(s_iowow_compound_test) { |
| 126 | + RUN_TEST(t_iowow_compound_test1); |
| 127 | + if (isatty(STDOUT_FILENO)) { |
| 128 | + RUN_TEST(t_iowow_compound_test2); |
| 129 | + } |
| 130 | +} |
| 131 | + |
| 132 | +GREATEST_MAIN_DEFS(); |
| 133 | + |
| 134 | +int main(int argc, char **argv) { |
| 135 | + GREATEST_MAIN_BEGIN(); |
| 136 | + RUN_SUITE(s_iowow_compound_test); |
| 137 | + GREATEST_MAIN_END(); |
| 138 | +} |
0 commit comments