plugins/sql: make columns an array of pointers.
`struct column` has a dynamically allocated member, which is neater if it is a tal object itself (we allocated the member off the array, instead). We're about to add two new members, so clean this up first. Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
This commit is contained in:
101
plugins/sql.c
101
plugins/sql.c
@@ -101,7 +101,7 @@ struct table_desc {
|
||||
const char *name;
|
||||
/* e.g. "payments" for listsendpays */
|
||||
const char *arrname;
|
||||
struct column *columns;
|
||||
struct column **columns;
|
||||
char *update_stmt;
|
||||
/* If we are a subtable */
|
||||
struct table_desc *parent;
|
||||
@@ -431,7 +431,7 @@ static struct command_result *process_json_subobjs(struct command *cmd,
|
||||
u64 this_rowid)
|
||||
{
|
||||
for (size_t i = 0; i < tal_count(td->columns); i++) {
|
||||
const struct column *col = &td->columns[i];
|
||||
const struct column *col = td->columns[i];
|
||||
struct command_result *ret;
|
||||
const jsmntok_t *coltok;
|
||||
|
||||
@@ -477,7 +477,7 @@ static struct command_result *process_json_obj(struct command *cmd,
|
||||
|
||||
/* FIXME: This is O(n^2): hash td->columns and look up the other way. */
|
||||
for (size_t i = 0; i < tal_count(td->columns); i++) {
|
||||
const struct column *col = &td->columns[i];
|
||||
const struct column *col = td->columns[i];
|
||||
const jsmntok_t *coltok;
|
||||
|
||||
if (col->sub) {
|
||||
@@ -1054,13 +1054,13 @@ static void json_add_columns(struct json_stream *js,
|
||||
const struct table_desc *td)
|
||||
{
|
||||
for (size_t i = 0; i < tal_count(td->columns); i++) {
|
||||
if (td->columns[i].sub) {
|
||||
if (td->columns[i].sub->is_subobject)
|
||||
json_add_columns(js, td->columns[i].sub);
|
||||
if (td->columns[i]->sub) {
|
||||
if (td->columns[i]->sub->is_subobject)
|
||||
json_add_columns(js, td->columns[i]->sub);
|
||||
continue;
|
||||
}
|
||||
json_add_column(js, td->columns[i].dbname,
|
||||
fieldtypemap[td->columns[i].ftype].sqltype);
|
||||
json_add_column(js, td->columns[i]->dbname,
|
||||
fieldtypemap[td->columns[i]->ftype].sqltype);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1142,7 +1142,7 @@ static void add_sub_object(char **update_stmt, char **create_stmt,
|
||||
|
||||
/* sub-objects are folded into this table. */
|
||||
for (size_t j = 0; j < tal_count(sub->columns); j++) {
|
||||
const struct column *subcol = &sub->columns[j];
|
||||
const struct column *subcol = sub->columns[j];
|
||||
|
||||
if (subcol->sub) {
|
||||
add_sub_object(update_stmt, create_stmt, sep,
|
||||
@@ -1192,7 +1192,7 @@ static void finish_td(struct plugin *plugin, struct table_desc *td)
|
||||
}
|
||||
|
||||
for (size_t i = 0; i < tal_count(td->columns); i++) {
|
||||
const struct column *col = &td->columns[i];
|
||||
const struct column *col = td->columns[i];
|
||||
|
||||
if (col->sub) {
|
||||
add_sub_object(&td->update_stmt, &create_stmt,
|
||||
@@ -1216,7 +1216,7 @@ static void finish_td(struct plugin *plugin, struct table_desc *td)
|
||||
do_subtables:
|
||||
/* Now do any children */
|
||||
for (size_t i = 0; i < tal_count(td->columns); i++) {
|
||||
const struct column *col = &td->columns[i];
|
||||
const struct column *col = td->columns[i];
|
||||
if (col->sub)
|
||||
finish_td(plugin, col->sub);
|
||||
}
|
||||
@@ -1261,7 +1261,8 @@ static const char *db_table_name(const tal_t *ctx, const char *cmdname)
|
||||
return ret;
|
||||
}
|
||||
|
||||
static struct table_desc *new_table_desc(struct table_desc *parent,
|
||||
static struct table_desc *new_table_desc(const tal_t *ctx,
|
||||
struct table_desc *parent,
|
||||
const jsmntok_t *cmd,
|
||||
const jsmntok_t *arrname,
|
||||
bool is_subobject)
|
||||
@@ -1269,7 +1270,7 @@ static struct table_desc *new_table_desc(struct table_desc *parent,
|
||||
struct table_desc *td;
|
||||
const char *name;
|
||||
|
||||
td = tal(parent, struct table_desc);
|
||||
td = tal(ctx, struct table_desc);
|
||||
td->cmdname = json_strdup(td, schemas, cmd);
|
||||
name = db_table_name(tmpctx, td->cmdname);
|
||||
if (!parent)
|
||||
@@ -1279,7 +1280,7 @@ static struct table_desc *new_table_desc(struct table_desc *parent,
|
||||
td->parent = parent;
|
||||
td->is_subobject = is_subobject;
|
||||
td->arrname = json_strdup(td, schemas, arrname);
|
||||
td->columns = tal_arr(td, struct column, 0);
|
||||
td->columns = tal_arr(td, struct column *, 0);
|
||||
if (streq(td->name, "channels"))
|
||||
td->refresh = channels_refresh;
|
||||
else if (streq(td->name, "nodes"))
|
||||
@@ -1298,7 +1299,7 @@ static bool find_column(const struct table_desc *td,
|
||||
const char *dbname)
|
||||
{
|
||||
for (size_t i = 0; i < tal_count(td->columns); i++) {
|
||||
if (streq(td->columns[i].dbname, dbname))
|
||||
if (streq(td->columns[i]->dbname, dbname))
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
@@ -1312,19 +1313,19 @@ static void add_table_singleton(struct table_desc *td,
|
||||
const jsmntok_t *name,
|
||||
const jsmntok_t *tok)
|
||||
{
|
||||
struct column col;
|
||||
struct column *col = tal(td->columns, struct column);
|
||||
const jsmntok_t *type;
|
||||
|
||||
/* FIXME: We would need to return false here and delete table! */
|
||||
assert(!ignore_column(td, tok));
|
||||
type = json_get_member(schemas, tok, "type");
|
||||
|
||||
col.ftype = find_fieldtype(type);
|
||||
col.sub = NULL;
|
||||
col->ftype = find_fieldtype(type);
|
||||
col->sub = NULL;
|
||||
/* We name column after the JSON parent field; but jsonname is NULL so we
|
||||
* know to expect an array not a member. */
|
||||
col.dbname = db_column_name(td->columns, td, name);
|
||||
col.jsonname = NULL;
|
||||
col->dbname = db_column_name(col, td, name);
|
||||
col->jsonname = NULL;
|
||||
tal_arr_expand(&td->columns, col);
|
||||
}
|
||||
|
||||
@@ -1360,7 +1361,7 @@ static void add_table_properties(struct table_desc *td,
|
||||
|
||||
json_for_each_obj(i, t, properties) {
|
||||
const jsmntok_t *type;
|
||||
struct column col;
|
||||
struct column *col;
|
||||
|
||||
if (ignore_column(td, t))
|
||||
continue;
|
||||
@@ -1370,10 +1371,14 @@ static void add_table_properties(struct table_desc *td,
|
||||
if (!type)
|
||||
continue;
|
||||
|
||||
col = tal(td->columns, struct column);
|
||||
|
||||
/* Depends on when it was deprecated, and whether deprecations
|
||||
* are enabled! */
|
||||
if (is_deprecated(schemas, t+1))
|
||||
if (is_deprecated(schemas, t+1)) {
|
||||
tal_free(col);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (json_tok_streq(schemas, type, "array")) {
|
||||
const jsmntok_t *items;
|
||||
@@ -1381,25 +1386,25 @@ static void add_table_properties(struct table_desc *td,
|
||||
items = json_get_member(schemas, t+1, "items");
|
||||
type = json_get_member(schemas, items, "type");
|
||||
|
||||
col.sub = new_table_desc(td, t, t, false);
|
||||
col->sub = new_table_desc(col, td, t, t, false);
|
||||
/* Array of primitives? Treat as single-entry obj */
|
||||
if (!json_tok_streq(schemas, type, "object"))
|
||||
add_table_singleton(col.sub, t, items);
|
||||
add_table_singleton(col->sub, t, items);
|
||||
else
|
||||
add_table_object(col.sub, items);
|
||||
add_table_object(col->sub, items);
|
||||
} else if (json_tok_streq(schemas, type, "object")) {
|
||||
col.sub = new_table_desc(td, t, t, true);
|
||||
add_table_object(col.sub, t+1);
|
||||
col->sub = new_table_desc(col, td, t, t, true);
|
||||
add_table_object(col->sub, t+1);
|
||||
} else {
|
||||
col.ftype = find_fieldtype(type);
|
||||
col.sub = NULL;
|
||||
col->ftype = find_fieldtype(type);
|
||||
col->sub = NULL;
|
||||
}
|
||||
col.dbname = db_column_name(td->columns, td, t);
|
||||
col->dbname = db_column_name(col, td, t);
|
||||
/* Some schemas repeat, assume they're the same */
|
||||
if (find_column(td, col.dbname)) {
|
||||
tal_free(col.dbname);
|
||||
if (find_column(td, col->dbname)) {
|
||||
tal_free(col);
|
||||
} else {
|
||||
col.jsonname = json_strdup(td->columns, schemas, t);
|
||||
col->jsonname = json_strdup(col, schemas, t);
|
||||
tal_arr_expand(&td->columns, col);
|
||||
}
|
||||
}
|
||||
@@ -1434,8 +1439,14 @@ static void add_table_object(struct table_desc *td, const jsmntok_t *tok)
|
||||
static void init_tablemap(struct plugin *plugin)
|
||||
{
|
||||
const jsmntok_t *toks, *t;
|
||||
const tal_t *ctx;
|
||||
size_t i;
|
||||
|
||||
if (plugin)
|
||||
ctx = plugin;
|
||||
else
|
||||
ctx = tmpctx;
|
||||
|
||||
strmap_init(&tablemap);
|
||||
|
||||
toks = json_parse_simple(tmpctx, schemas, strlen(schemas));
|
||||
@@ -1451,11 +1462,7 @@ static void init_tablemap(struct plugin *plugin)
|
||||
type = json_get_member(schemas, items, "type");
|
||||
assert(json_tok_streq(schemas, type, "object"));
|
||||
|
||||
td = new_table_desc(NULL, t, cmd, false);
|
||||
if (plugin)
|
||||
tal_steal(plugin, td);
|
||||
else
|
||||
tal_steal(tmpctx, td);
|
||||
td = new_table_desc(ctx, NULL, t, cmd, false);
|
||||
add_table_object(td, items);
|
||||
|
||||
if (plugin)
|
||||
@@ -1543,8 +1550,8 @@ static void print_columns(const struct table_desc *td, const char *indent,
|
||||
{
|
||||
for (size_t i = 0; i < tal_count(td->columns); i++) {
|
||||
const char *origin;
|
||||
if (td->columns[i].sub) {
|
||||
const struct table_desc *subtd = td->columns[i].sub;
|
||||
if (td->columns[i]->sub) {
|
||||
const struct table_desc *subtd = td->columns[i]->sub;
|
||||
|
||||
if (!subtd->is_subobject) {
|
||||
const char *subindent;
|
||||
@@ -1561,23 +1568,23 @@ static void print_columns(const struct table_desc *td, const char *indent,
|
||||
|
||||
subobjsrc = tal_fmt(tmpctx,
|
||||
", from JSON object `%s`",
|
||||
td->columns[i].jsonname);
|
||||
td->columns[i]->jsonname);
|
||||
print_columns(subtd, indent, subobjsrc);
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
if (streq(objsrc, "")
|
||||
&& td->columns[i].jsonname
|
||||
&& !streq(td->columns[i].dbname, td->columns[i].jsonname)) {
|
||||
&& td->columns[i]->jsonname
|
||||
&& !streq(td->columns[i]->dbname, td->columns[i]->jsonname)) {
|
||||
origin = tal_fmt(tmpctx, ", from JSON field `%s`",
|
||||
td->columns[i].jsonname);
|
||||
td->columns[i]->jsonname);
|
||||
} else
|
||||
origin = "";
|
||||
printf("%s- `%s` (type `%s`, sqltype `%s`%s%s)\n",
|
||||
indent, td->columns[i].dbname,
|
||||
fieldtypemap[td->columns[i].ftype].name,
|
||||
fieldtypemap[td->columns[i].ftype].sqltype,
|
||||
indent, td->columns[i]->dbname,
|
||||
fieldtypemap[td->columns[i]->ftype].name,
|
||||
fieldtypemap[td->columns[i]->ftype].sqltype,
|
||||
origin, objsrc);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user