All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
as_rec.h
Go to the documentation of this file.
1 /*
2  * Copyright 2008-2017 Aerospike, Inc.
3  *
4  * Portions may be licensed to Aerospike, Inc. under one or more contributor
5  * license agreements.
6  *
7  * Licensed under the Apache License, Version 2.0 (the "License"); you may not
8  * use this file except in compliance with the License. You may obtain a copy of
9  * the License at http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
13  * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
14  * License for the specific language governing permissions and limitations under
15  * the License.
16  */
17 
18 #pragma once
19 
20 #include <aerospike/as_integer.h>
21 #include <aerospike/as_bytes.h>
22 #include <aerospike/as_geojson.h>
23 #include <aerospike/as_list.h>
24 #include <aerospike/as_map.h>
25 #include <aerospike/as_string.h>
26 #include <aerospike/as_util.h>
27 #include <aerospike/as_val.h>
28 
29 #include <stdbool.h>
30 #include <stdint.h>
31 
32 #ifdef __cplusplus
33 extern "C" {
34 #endif
35 
36 /******************************************************************************
37  * TYPES
38  *****************************************************************************/
39 
40 struct as_rec_hooks_s;
41 
42 /**
43  * Callback function for `as_rec_bin_names()`. Used for porting bin names
44  * to Lua.
45  *
46  * @param bin_names A string containing the (null-terminated) bin names.
47  * @param nbins The number of bins in the record.
48  * @param max_name_size The maximum length of a bin name.
49  * @param udata User-provided data.
50  */
51 typedef void (* as_rec_bin_names_callback) (char * bin_names, uint32_t nbins, uint16_t max_name_size, void * udata);
52 
53 /**
54  * Callback function for `as_rec_foreach()`. Called for each bin in the
55  * record.
56  *
57  * @param name The name of the current bin.
58  * @param value The value of the current bin.
59  * @param udata The user-data provided to the `as_rec_foreach()`.
60  *
61  * @return true to continue iterating through the list.
62  * false to stop iterating.
63  */
64 typedef bool (* as_rec_foreach_callback) (const char * name, const as_val * value, void * udata);
65 
66 /**
67  * as_rec is an interface for record types. A record is how data in Aerospike
68  * is represented, and is composed of bins and metadata.
69  *
70  * Implementations:
71  * - as_record
72  *
73  * @extends as_val
74  * @ingroup aerospike_t
75  */
76 typedef struct as_rec_s {
77 
78  /**
79  * @private
80  * as_rec is a subtype of as_val.
81  * You can cast as_rec to as_val.
82  */
83  as_val _;
84 
85  /**
86  * Data provided by the implementation of `as_rec`.
87  */
88  void * data;
89 
90  /**
91  * Hooks provided by the implementation of `as_rec`.
92  */
93  const struct as_rec_hooks_s * hooks;
94 
95 } as_rec;
96 
97 /**
98  * Record Hooks.
99  *
100  * An implementation of `as_rec` should provide implementations for each
101  * of the hooks.
102  */
103 typedef struct as_rec_hooks_s {
104 
105  /**
106  * Destroy the record.
107  */
108  bool (* destroy)(as_rec * rec);
109 
110  /**
111  * Get the hashcode of the record.
112  */
113  uint32_t (* hashcode)(const as_rec * rec);
114 
115  /**
116  * Get the value of the bin in the record.
117  */
118  as_val * (* get)(const as_rec * rec, const char * name);
119 
120  /**
121  * Set the value of the bin in the record.
122  */
123  int (* set)(const as_rec * rec, const char * name, const as_val * value);
124 
125  /**
126  * Remove the bin from the record.
127  */
128  int (* remove)(const as_rec * rec, const char * bin);
129 
130  /**
131  * Get the ttl value of the record.
132  */
133  uint32_t (* ttl)(const as_rec * rec);
134 
135  /**
136  * Get the last update time of the record.
137  */
138  uint64_t (* last_update_time)(const as_rec * rec);
139 
140  /**
141  * Get the generation value of the record.
142  */
143  uint16_t (* gen)(const as_rec * rec);
144 
145  /**
146  * Get the record's key.
147  */
148  as_val * (* key)(const as_rec * rec);
149 
150  /**
151  * Get the record's set name.
152  */
153  const char * (* setname)(const as_rec * rec);
154 
155  /**
156  * Get the number of bins of the record.
157  */
158  uint16_t (* numbins)(const as_rec * rec);
159 
160  /**
161  * Get a list of the record's bin names.
162  */
163  int (* bin_names)(const as_rec * rec, as_rec_bin_names_callback callback, void * udata);
164 
165  /**
166  * Get the digest of the record.
167  */
168  as_bytes * (* digest)(const as_rec * rec);
169 
170  /**
171  * Set the time to live (ttl) of the record.
172  */
173  int (* set_ttl)(const as_rec * rec, uint32_t ttl);
174 
175  /**
176  * Discard the record's key.
177  */
178  int (* drop_key)(const as_rec * rec);
179 
180  /**
181  * Iterate over each bin in the record.
182  */
183  bool (* foreach)(const as_rec * rec, as_rec_foreach_callback callback, void * udata);
184 
185 } as_rec_hooks;
186 
187 /******************************************************************************
188  * INSTANCE FUNCTIONS
189  *****************************************************************************/
190 
191 /**
192  * @private
193  * Utilized by subtypes of as_rec to initialize the parent.
194  *
195  * @param rec The record to initialize
196  * @param free If TRUE, then as_rec_destory() will free the record.
197  * @param data Data for the map.
198  * @param hooks Implementation for the map interface.
199  *
200  * @return The initialized as_map on success. Otherwise NULL.
201  *
202  * @relatesalso as_rec
203  */
204 as_rec * as_rec_cons(as_rec * rec, bool free, void * data, const as_rec_hooks * hooks);
205 
206 /**
207  * Initialize a stack allocated record.
208  *
209  * @param rec Stack allocated record to initialize.
210  * @param data Data for the record.
211  * @param hooks Implementation for the record interface.
212  *
213  * @return On success, the initialized record. Otherwise NULL.
214  *
215  * @relatesalso as_rec
216  */
217 as_rec * as_rec_init(as_rec * rec, void * data, const as_rec_hooks * hooks);
218 
219 /**
220  * Create and initialize a new heap allocated record.
221  *
222  * @param data Data for the record.
223  * @param hooks Implementation for the record interface.
224  *
225  * @return On success, a new record. Otherwise NULL.
226  *
227  * @relatesalso as_rec
228  */
229 as_rec * as_rec_new(void * data, const as_rec_hooks * hooks);
230 
231 /**
232  * Destroy the record.
233  *
234  * @relatesalso as_rec
235  */
236 static inline void as_rec_destroy(as_rec * rec)
237 {
238  as_val_destroy((as_val *) rec);
239 }
240 
241 /******************************************************************************
242  * INLINE FUNCTIONS
243  ******************************************************************************/
244 
245 /**
246  * Get the data source for the record.
247  *
248  * @relatesalso as_rec
249  */
250 static inline void * as_rec_source(const as_rec * rec)
251 {
252  return rec ? rec->data : NULL;
253 }
254 
255 /**
256  * Set bin value to nil. This will instruct the server to remove the bin when the
257  * record is written using aerospike_key_put().
258  *
259  * @param rec The record to remove the bin from.
260  * @param name The name of the bin to remove.
261  *
262  * @return 0 on success, otherwise an error occurred.
263  *
264  * @relatesalso as_rec
265  */
266 static inline int as_rec_remove(const as_rec * rec, const char * name)
267 {
268  return as_util_hook(remove, 1, rec, name);
269 }
270 
271 /**
272  * Get the ttl for the record.
273  *
274  * @relatesalso as_rec
275  */
276 static inline uint32_t as_rec_ttl(const as_rec * rec)
277 {
278  return as_util_hook(ttl, 0, rec);
279 }
280 
281 /**
282  * Get the last update time for the record.
283  *
284  * @relatesalso as_rec
285  */
286 static inline uint64_t as_rec_last_update_time(const as_rec * rec)
287 {
288  return as_util_hook(last_update_time, 0, rec);
289 }
290 
291 /**
292  * Get the generation of the record
293  *
294  * @relatesalso as_rec
295  */
296 static inline uint16_t as_rec_gen(const as_rec * rec)
297 {
298  return as_util_hook(gen, 0, rec);
299 }
300 
301 /**
302  * Get the record's key.
303  *
304  * @relatesalso as_rec
305  */
306 static inline as_val * as_rec_key(const as_rec * rec)
307 {
308  return as_util_hook(key, 0, rec);
309 }
310 
311 /**
312  * Get the record's set name.
313  *
314  * @relatesalso as_rec
315  */
316 static inline const char * as_rec_setname(const as_rec * rec)
317 {
318  return as_util_hook(setname, 0, rec);
319 }
320 
321 /**
322  * Get the number of bins in the record.
323  *
324  * @relatesalso as_rec
325  */
326 static inline uint16_t as_rec_numbins(const as_rec * rec)
327 {
328  return as_util_hook(numbins, 0, rec);
329 }
330 
331 /**
332  * Get a list of the bin names in the record.
333  *
334  * @relatesalso as_rec
335  */
336 static inline int as_rec_bin_names(const as_rec * rec, as_rec_bin_names_callback callback, void * udata)
337 {
338  return as_util_hook(bin_names, 0, rec, callback, udata);
339 }
340 
341 /**
342  * Get the digest of the record.
343  *
344  * @relatesalso as_rec
345  */
346 static inline as_bytes * as_rec_digest(const as_rec * rec)
347 {
348  return as_util_hook(digest, 0, rec);
349 }
350 
351 /**
352  * Set the time to live (ttl).
353  *
354  * @relatesalso as_rec
355  */
356 static inline int as_rec_set_ttl(const as_rec * rec, uint32_t ttl)
357 {
358  return as_util_hook(set_ttl, 0, rec, ttl);
359 }
360 
361 /**
362  * Drop the record's key.
363  *
364  * @relatesalso as_rec
365  */
366 static inline int as_rec_drop_key(const as_rec * rec)
367 {
368  return as_util_hook(drop_key, 0, rec);
369 }
370 
371 /******************************************************************************
372  * BIN GETTER FUNCTIONS
373  ******************************************************************************/
374 
375 /**
376  * Get a bin's value.
377  *
378  * @param rec The as_rec to read the bin value from.
379  * @param name The name of the bin.
380  *
381  * @return On success, the value of the bin. Otherwise NULL.
382  *
383  * @relatesalso as_rec
384  */
385 static inline as_val * as_rec_get(const as_rec * rec, const char * name)
386 {
387  return as_util_hook(get, NULL, rec, name);
388 }
389 
390 /**
391  * Get a bin's value as an int64_t.
392  *
393  * @param rec The as_rec to read the bin value from.
394  * @param name The name of the bin.
395  *
396  * @return On success, the value of the bin. Otherwise 0.
397  *
398  * @relatesalso as_rec
399  */
400 static inline int64_t as_rec_get_int64(const as_rec * rec, const char * name)
401 {
402  as_val * v = as_util_hook(get, NULL, rec, name);
404  return i ? as_integer_toint(i) : 0;
405 }
406 
407 /**
408  * Get a bin's value as a double.
409  *
410  * @param rec The as_rec to read the bin value from.
411  * @param name The name of the bin.
412  *
413  * @return On success, the value of the bin. Otherwise 0.
414  *
415  * @relatesalso as_rec
416  */
417 static inline double as_rec_get_double(const as_rec * rec, const char * name)
418 {
419  as_val * v = as_util_hook(get, NULL, rec, name);
420  as_double * ptr = as_double_fromval(v);
421  return ptr ? ptr->value : 0.0;
422 }
423 
424 /**
425  * Get a bin's value as a NULL terminated string.
426  *
427  * @param rec The as_rec to read the bin value from.
428  * @param name The name of the bin.
429  *
430  * @return On success, the value of the bin. Otherwise NULL.
431  *
432  * @relatesalso as_rec
433  */
434 static inline char * as_rec_get_str(const as_rec * rec, const char * name)
435 {
436  as_val * v = as_util_hook(get, NULL, rec, name);
437  as_string * s = as_string_fromval(v);
438  return s ? as_string_tostring(s) : 0;
439 }
440 
441 /**
442  * Get a bin's value as a NULL terminated GeoJSON string.
443  *
444  * @param rec The as_rec to read the bin value from.
445  * @param name The name of the bin.
446  *
447  * @return On success, the value of the bin. Otherwise NULL.
448  *
449  * @relatesalso as_rec
450  */
451 static inline char * as_rec_get_geojson_str(const as_rec * rec, const char * name)
452 {
453  as_val * v = as_util_hook(get, NULL, rec, name);
455  return as_geojson_get(s);
456 }
457 
458 /**
459  * Get a bin's value as an as_integer.
460  *
461  * @param rec The as_rec to read the bin value from.
462  * @param name The name of the bin.
463  *
464  * @return On success, the value of the bin. Otherwise NULL.
465  *
466  * @relatesalso as_rec
467  */
468 static inline as_integer * as_rec_get_integer(const as_rec * rec, const char * name)
469 {
470  as_val * v = as_util_hook(get, NULL, rec, name);
471  return as_integer_fromval(v);
472 }
473 
474 /**
475  * Get a bin's value as an as_double.
476  *
477  * @param rec The as_rec to read the bin value from.
478  * @param name The name of the bin.
479  *
480  * @return On success, the value of the bin. Otherwise NULL.
481  *
482  * @relatesalso as_rec
483  */
484 static inline as_double * as_rec_get_as_double(const as_rec * rec, const char * name)
485 {
486  as_val * v = as_util_hook(get, NULL, rec, name);
487  return as_double_fromval(v);
488 }
489 
490 /**
491  * Get a bin's value as an as_string.
492  *
493  * @param rec The as_rec to read the bin value from.
494  * @param name The name of the bin.
495  *
496  * @return On success, the value of the bin. Otherwise NULL.
497  *
498  * @relatesalso as_rec
499  */
500 static inline as_string * as_rec_get_string(const as_rec * rec, const char * name)
501 {
502  as_val * v = as_util_hook(get, NULL, rec, name);
503  return as_string_fromval(v);
504 }
505 
506 /**
507  * Get a bin's value as an as_geojson.
508  *
509  * @param rec The as_rec to read the bin value from.
510  * @param name The name of the bin.
511  *
512  * @return On success, the value of the bin. Otherwise NULL.
513  *
514  * @relatesalso as_rec
515  */
516 static inline as_geojson * as_rec_get_geojson(const as_rec * rec, const char * name)
517 {
518  as_val * v = as_util_hook(get, NULL, rec, name);
519  return as_geojson_fromval(v);
520 }
521 
522 /**
523  * Get a bin's value as an as_bytes.
524  *
525  * @param rec The as_rec to read the bin value from.
526  * @param name The name of the bin.
527  *
528  * @return On success, the value of the bin. Otherwise NULL.
529  *
530  * @relatesalso as_rec
531  */
532 static inline as_bytes * as_rec_get_bytes(const as_rec * rec, const char * name)
533 {
534  as_val * v = as_util_hook(get, NULL, rec, name);
535  return as_bytes_fromval(v);
536 }
537 
538 /**
539  * Get a bin's value as an as_list.
540  *
541  * @param rec The as_rec to read the bin value from.
542  * @param name The name of the bin.
543  *
544  * @return On success, the value of the bin. Otherwise NULL.
545  *
546  * @relatesalso as_rec
547  */
548 static inline as_list * as_rec_get_list(const as_rec * rec, const char * name)
549 {
550  as_val * v = as_util_hook(get, NULL, rec, name);
551  return as_list_fromval(v);
552 }
553 
554 /**
555  * Get a bin's value as an as_map.
556  *
557  * @param rec The as_rec to read the bin value from.
558  * @param name The name of the bin.
559  *
560  * @return On success, the value of the bin. Otherwise NULL.
561  *
562  * @relatesalso as_rec
563  */
564 static inline as_map * as_rec_get_map(const as_rec * rec, const char * name)
565 {
566  as_val * v = as_util_hook(get, NULL, rec, name);
567  return as_map_fromval(v);
568 }
569 
570 /******************************************************************************
571  * BIN SETTER FUNCTIONS
572  ******************************************************************************/
573 
574 /**
575  * Set the bin's value to an as_val.
576  *
577  * @param rec The as_rec to write the bin value to - CONSUMES REFERENCE
578  * @param name The name of the bin.
579  * @param value The value of the bin.
580  *
581  * @return On success, 0. Otherwise an error occurred.
582  *
583  * @relatesalso as_rec
584  */
585 static inline int as_rec_set(const as_rec * rec, const char * name, const as_val * value)
586 {
587  return as_util_hook(set, 1, rec, name, value);
588 }
589 
590 /**
591  * Set the bin's value to an int64_t.
592  *
593  * @param rec The as_rec storing the bin.
594  * @param name The name of the bin.
595  * @param value The value of the bin.
596  *
597  * @return On success, 0. Otherwise an error occurred.
598  *
599  * @relatesalso as_rec
600  */
601 static inline int as_rec_set_int64(const as_rec * rec, const char * name, int64_t value)
602 {
603  return as_util_hook(set, 1, rec, name, (as_val *) as_integer_new(value));
604 }
605 
606 /**
607  * Set the bin's value to a double.
608  *
609  * @param rec The as_rec storing the bin.
610  * @param name The name of the bin.
611  * @param value The value of the bin.
612  *
613  * @return On success, 0. Otherwise an error occurred.
614  *
615  * @relatesalso as_rec
616  */
617 static inline int as_rec_set_double(const as_rec * rec, const char * name, double value)
618 {
619  return as_util_hook(set, 1, rec, name, (as_val *) as_double_new(value));
620 }
621 
622 /**
623  * Set the bin's value to a NULL terminated string.
624  *
625  * @param rec The as_rec storing the bin.
626  * @param name The name of the bin.
627  * @param value The value of the bin.
628  *
629  * @return On success, 0. Otherwise an error occurred.
630  *
631  * @relatesalso as_rec
632  */
633 static inline int as_rec_set_str(const as_rec * rec, const char * name, const char * value)
634 {
635  return as_util_hook(set, 1, rec, name, (as_val *) as_string_new_strdup(value));
636 }
637 
638 /**
639  * Set the bin's value to an as_integer.
640  *
641  * @param rec The as_rec storing the bin.
642  * @param name The name of the bin.
643  * @param value The value of the bin.
644  *
645  * @return On success, 0. Otherwise an error occurred.
646  *
647  * @relatesalso as_rec
648  */
649 static inline int as_rec_set_integer(const as_rec * rec, const char * name, const as_integer * value)
650 {
651  return as_util_hook(set, 1, rec, name, (as_val *) value);
652 }
653 
654 /**
655  * Set the bin's value to an as_double.
656  *
657  * @param rec The as_rec storing the bin.
658  * @param name The name of the bin.
659  * @param value The value of the bin.
660  *
661  * @return On success, 0. Otherwise an error occurred.
662  *
663  * @relatesalso as_rec
664  */
665 static inline int as_rec_set_as_double(const as_rec * rec, const char * name, const as_double * value)
666 {
667  return as_util_hook(set, 1, rec, name, (as_val *) value);
668 }
669 
670 /**
671  * Set the bin's value to an as_string.
672  *
673  * @param rec The as_rec storing the bin.
674  * @param name The name of the bin.
675  * @param value The value of the bin.
676  *
677  * @return On success, 0. Otherwise an error occurred.
678  *
679  * @relatesalso as_rec
680  */
681 static inline int as_rec_set_string(const as_rec * rec, const char * name, const as_string * value)
682 {
683  return as_util_hook(set, 1, rec, name, (as_val *) value);
684 }
685 
686 /**
687  * Set the bin's value to an as_geojson.
688  *
689  * @param rec The as_rec storing the bin.
690  * @param name The name of the bin.
691  * @param value The value of the bin.
692  *
693  * @return On success, 0. Otherwise an error occurred.
694  *
695  * @relatesalso as_rec
696  */
697 static inline int as_rec_set_geojson(const as_rec * rec, const char * name, const as_geojson * value)
698 {
699  return as_util_hook(set, 1, rec, name, (as_val *) value);
700 }
701 
702 /**
703  * Set the bin's value to an as_bytes.
704  *
705  * @param rec The as_rec storing the bin.
706  * @param name The name of the bin.
707  * @param value The value of the bin.
708  *
709  * @return On success, 0. Otherwise an error occurred.
710  *
711  * @relatesalso as_rec
712  */
713 static inline int as_rec_set_bytes(const as_rec * rec, const char * name, const as_bytes * value)
714 {
715  return as_util_hook(set, 1, rec, name, (as_val *) value);
716 }
717 
718 /**
719  * Set the bin's value to an as_list.
720  *
721  * @param rec The as_rec storing the bin.
722  * @param name The name of the bin.
723  * @param value The value of the bin.
724  *
725  * @return On success, 0. Otherwise an error occurred.
726  *
727  * @relatesalso as_rec
728  */
729 static inline int as_rec_set_list(const as_rec * rec, const char * name, const as_list * value)
730 {
731  return as_util_hook(set, 1, rec, name, (as_val *) value);
732 }
733 
734 /**
735  * Set the bin's value to an as_map.
736  *
737  * @param rec The as_rec storing the bin.
738  * @param name The name of the bin.
739  * @param value The value of the bin.
740  *
741  * @return On success, 0. Otherwise an error occurred.
742  *
743  * @relatesalso as_rec
744  */
745 static inline int as_rec_set_map(const as_rec * rec, const char * name, const as_map * value)
746 {
747  return as_util_hook(set, 1, rec, name, (as_val *) value);
748 }
749 
750 /******************************************************************************
751  * ITERATION FUNCTIONS
752  ******************************************************************************/
753 
754 /**
755  * Call the callback function for each bin in the record.
756  *
757  * @param rec The as_rec containing the bins to iterate over.
758  * @param callback The function to call for each entry.
759  * @param udata User-data to be passed to the callback.
760  *
761  * @return true if iteration completes fully. false if iteration was aborted.
762  *
763  * @relatesalso as_rec
764  */
765 static inline bool as_rec_foreach(const as_rec * rec, as_rec_foreach_callback callback, void * udata)
766 {
767  return as_util_hook(foreach, false, rec, callback, udata);
768 }
769 
770 /******************************************************************************
771  * CONVERSION FUNCTIONS
772  ******************************************************************************/
773 
774 /**
775  * Convert to an as_val.
776  *
777  * @relatesalso as_rec
778  */
779 static inline as_val * as_rec_toval(const as_rec * rec)
780 {
781  return (as_val *) rec;
782 }
783 
784 /**
785  * Convert from an as_val.
786  *
787  * @relatesalso as_rec
788  */
789 static inline as_rec * as_rec_fromval(const as_val * v)
790 {
791  return as_util_fromval(v, AS_REC, as_rec);
792 }
793 
794 /******************************************************************************
795  * as_val FUNCTIONS
796  ******************************************************************************/
797 
798 /**
799  * @private
800  * Internal helper function for destroying an as_val.
801  */
802 void as_rec_val_destroy(as_val *);
803 
804 /**
805  * @private
806  * Internal helper function for getting the hashcode of an as_val.
807  */
808 uint32_t as_rec_val_hashcode(const as_val *v);
809 
810 /**
811  * @private
812  * Internal helper function for getting the string representation of an as_val.
813  */
814 char * as_rec_val_tostring(const as_val *v);
815 
816 #ifdef __cplusplus
817 } // end extern "C"
818 #endif