Collation routines order the results from a SELECT statement. You can define your own routines and tell QDB to use them by providing the COLLATE keyword in the ORDER BY clause.
In your code, you must define a collation routine by providing both a setup function and a sorting function. You must also define a qdb_collation structure that references these functions. Consider this sample collation that provides a setup function that allows the caller to reverse the sorting order (by passing in the string "reverse"), and then uses memcmp() in its sorting function:
typedef struct my_sort_cfg_s {
unsigned rev_sort;
} my_sort_cfg_t;
static ssize_t
my_sort_cfg_sort(void *arg, int l1, const void *s1,
int l2, const void *s2)
{
my_sort_cfg_t *my_sort_cfg = (my_sort_cfg_t *)arg;
int ret = memcmp(s1, s2, min(l1, l2));
return my_sort_cfg->rev_sort?-ret:ret;
}
static int
my_sort_cfg_setup(void *arg, const void *data,
int nbytes, char **errmsg)
{
my_sort_cfg_t *my_sort_cfg = (my_sort_cfg_t *)arg;
int ret=EOK;
char *buf;
if (!nbytes) {
return ret;
}
buf=alloca(nbytes+1);
if (!buf) {
return ret;
}
snprintf(buf, nbytes+1, "%s", (char*)data);
if (strcmp(buf, "reverse")) {
my_sort_cfg->rev_sort=1;
}
return(ret);
}
struct qdb_collation my_sort_runtime_cfg = {
.name="my_sort_runtime_cfg",
.encoding=SQLITE_UTF8,
.arg=&my_sort_cfg_data,
.compare=my_sort_cfg_sort,
.setup=my_sort_cfg_setup
};
In this case, the tag value for the structure is my_sort_runtime_cfg, the collation name as visible to SQL is also my_sort_runtime_cfg, the C function used for setup is my_sort_cfg_setup(), and the C function used for comparison is my_sort_cfg_sort(). Each function has the my_sort_cfg_data value passed in as its arg value. For more information on defining SQLite collation sequences, see the SQLite docs on sqlite3_create_collation().
You can define multiple collation sequences (in the same or different DLLs), but each must have a Collation entry in the configuration object as well as a struct qdb_collation object with a unique name describing the routine.
The qdb_collation structure has these members:
struct qdb_collation {
char *name;
int encoding;
void *arg;
int (*compare)(void *, int, const void *, int, const void *);
int (*setup)(void *, const void *, int, char **);
};
ssize_t sort(void *arg, int l1, const void *s1,
int l2, const void *s2);
int (*setup)(void *arg, const void *data, int nbytes, char **errmsg);