C, and other native languages
Nexyron exposes a C interface. Beyond C and C++ itself, this is the route for any language with a foreign-function interface: Go, C#, Java, Swift, Kotlin, Ruby, PHP and others can all call it.
Opening a database
#include <nexyron.h>
int main(void) {
nexyron_db *db = NULL;
if (nexyron_open("./business.nexyron", &db) != NEXYRON_OK) {
return 1;
}
nexyron_result *result = NULL;
if (nexyron_query(db, "MATCH (c:Customer) RETURN count(c) AS customers",
&result) == NEXYRON_OK) {
int64_t customers = 0;
nexyron_row_get_int(result, 0, "customers", &customers);
printf("%lld\n", (long long) customers);
nexyron_result_free(result);
}
nexyron_close(db);
return 0;
}
The rules that matter
Every call returns a status. Check it. A failed query returns a message explaining what was wrong and what to use instead; retrieve it rather than discarding it.
if (status != NEXYRON_OK) {
const char *message = nexyron_last_error(db);
fprintf(stderr, "nexyron: %s\n", message);
}
You free what you receive. Results are owned by the caller. Free each one when finished, and free the database last. In a long-running process a result that is never freed is a leak that grows with traffic.
Strings are UTF-8 and borrowed. A string returned from a result is valid until that result is freed. Copy it if it must outlive the result.
One database handle, shared. Open once, use from multiple threads, close on shutdown.
Binding from another language
Two things are worth doing in the wrapper rather than leaving to callers.
Tie freeing to your language's lifetime rules. Whatever your language calls
it: a destructor, a finalizer, defer, using, a context manager. Manual
freeing at every call site will eventually be forgotten.
Turn status codes into your language's errors. Carry the message through. The guidance in it is specific to the query that failed and is the main reason debugging is quick.
Beyond that, keep the wrapper thin. Parameters and typed rows are handled by the engine; a wrapper that re-implements them adds bugs rather than convenience.
Identifiers
Return identifiers as strings with element_id() when they will reach a runtime
without exact 64-bit integers, which includes JavaScript and some scripting
languages. In C itself they are exact, but a wrapper that returns strings keeps
one habit across every language you target.