mirror of
https://gitlab.gnome.org/GNOME/glib.git
synced 2024-12-25 15:06:14 +01:00
GSettings: new <schema> tags 'extends', 'list-of'
Add support for extends='' and list-of='' tags to the <schema> element. The attributes are parsed and some sanity-checking is done but currently nothing happens as a result. Add some tests.
This commit is contained in:
parent
101bfec676
commit
900a756e8f
@ -671,23 +671,34 @@ is_valid_keyname (const gchar *key,
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Handling of <schema> {{{1 */
|
/* Handling of <schema> {{{1 */
|
||||||
typedef struct
|
typedef struct _SchemaState SchemaState;
|
||||||
|
struct _SchemaState
|
||||||
{
|
{
|
||||||
gchar *path;
|
SchemaState *extends;
|
||||||
gchar *gettext_domain;
|
|
||||||
|
|
||||||
GHashTable *keys;
|
gchar *path;
|
||||||
} SchemaState;
|
gchar *gettext_domain;
|
||||||
|
gchar *extends_name;
|
||||||
|
gchar *list_of;
|
||||||
|
|
||||||
|
GHashTable *keys;
|
||||||
|
};
|
||||||
|
|
||||||
static SchemaState *
|
static SchemaState *
|
||||||
schema_state_new (const gchar *path,
|
schema_state_new (const gchar *path,
|
||||||
const gchar *gettext_domain)
|
const gchar *gettext_domain,
|
||||||
|
SchemaState *extends,
|
||||||
|
const gchar *extends_name,
|
||||||
|
const gchar *list_of)
|
||||||
{
|
{
|
||||||
SchemaState *state;
|
SchemaState *state;
|
||||||
|
|
||||||
state = g_slice_new (SchemaState);
|
state = g_slice_new (SchemaState);
|
||||||
state->path = g_strdup (path);
|
state->path = g_strdup (path);
|
||||||
state->gettext_domain = g_strdup (gettext_domain);
|
state->gettext_domain = g_strdup (gettext_domain);
|
||||||
|
state->extends = extends;
|
||||||
|
state->extends_name = g_strdup (extends_name);
|
||||||
|
state->list_of = g_strdup (list_of);
|
||||||
state->keys = g_hash_table_new_full (g_str_hash, g_str_equal,
|
state->keys = g_hash_table_new_full (g_str_hash, g_str_equal,
|
||||||
g_free, key_state_free);
|
g_free, key_state_free);
|
||||||
|
|
||||||
@ -740,6 +751,14 @@ schema_state_add_key (SchemaState *state,
|
|||||||
GString *enum_data;
|
GString *enum_data;
|
||||||
KeyState *key;
|
KeyState *key;
|
||||||
|
|
||||||
|
if (state->list_of)
|
||||||
|
{
|
||||||
|
g_set_error_literal (error, G_MARKUP_ERROR,
|
||||||
|
G_MARKUP_ERROR_INVALID_CONTENT,
|
||||||
|
"can not add keys to a list-of schema");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
if (!is_valid_keyname (name, error))
|
if (!is_valid_keyname (name, error))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
@ -809,13 +828,34 @@ typedef struct
|
|||||||
GString *string; /* non-NULL when accepting text */
|
GString *string; /* non-NULL when accepting text */
|
||||||
} ParseState;
|
} ParseState;
|
||||||
|
|
||||||
|
static gboolean
|
||||||
|
is_subclass (const gchar *class_name,
|
||||||
|
const gchar *possible_parent,
|
||||||
|
GHashTable *schema_table)
|
||||||
|
{
|
||||||
|
SchemaState *class;
|
||||||
|
|
||||||
|
if (strcmp (class_name, possible_parent) == 0)
|
||||||
|
return TRUE;
|
||||||
|
|
||||||
|
class = g_hash_table_lookup (schema_table, class_name);
|
||||||
|
g_assert (class != NULL);
|
||||||
|
|
||||||
|
return class->extends_name &&
|
||||||
|
is_subclass (class->extends_name, possible_parent, schema_table);
|
||||||
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
parse_state_start_schema (ParseState *state,
|
parse_state_start_schema (ParseState *state,
|
||||||
const gchar *id,
|
const gchar *id,
|
||||||
const gchar *path,
|
const gchar *path,
|
||||||
const gchar *gettext_domain,
|
const gchar *gettext_domain,
|
||||||
|
const gchar *extends_name,
|
||||||
|
const gchar *list_of,
|
||||||
GError **error)
|
GError **error)
|
||||||
{
|
{
|
||||||
|
SchemaState *extends;
|
||||||
|
|
||||||
if (g_hash_table_lookup (state->schema_table, id))
|
if (g_hash_table_lookup (state->schema_table, id))
|
||||||
{
|
{
|
||||||
g_set_error (error, G_MARKUP_ERROR,
|
g_set_error (error, G_MARKUP_ERROR,
|
||||||
@ -824,6 +864,66 @@ parse_state_start_schema (ParseState *state,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (extends_name)
|
||||||
|
{
|
||||||
|
extends = g_hash_table_lookup (state->schema_table, extends_name);
|
||||||
|
|
||||||
|
if (extends == NULL)
|
||||||
|
{
|
||||||
|
g_set_error (error, G_MARKUP_ERROR,
|
||||||
|
G_MARKUP_ERROR_INVALID_CONTENT,
|
||||||
|
"<schema id='%s'> extends not yet "
|
||||||
|
"existing schema '%s'", id, extends_name);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
extends = NULL;
|
||||||
|
|
||||||
|
if (list_of)
|
||||||
|
{
|
||||||
|
if (!g_hash_table_lookup (state->schema_table, list_of))
|
||||||
|
{
|
||||||
|
g_set_error (error, G_MARKUP_ERROR,
|
||||||
|
G_MARKUP_ERROR_INVALID_CONTENT,
|
||||||
|
"<schema id='%s'> is list of not yet "
|
||||||
|
"existing schema '%s'", id, list_of);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (extends)
|
||||||
|
{
|
||||||
|
if (list_of)
|
||||||
|
{
|
||||||
|
if (extends->list_of == NULL)
|
||||||
|
{
|
||||||
|
g_set_error (error, G_MARKUP_ERROR,
|
||||||
|
G_MARKUP_ERROR_INVALID_CONTENT,
|
||||||
|
"<schema id='%s'> is a list, extending "
|
||||||
|
"<schema id='%s'> which is not a list",
|
||||||
|
id, extends_name);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!is_subclass (list_of, extends->list_of, state->schema_table))
|
||||||
|
{
|
||||||
|
g_set_error (error, G_MARKUP_ERROR,
|
||||||
|
G_MARKUP_ERROR_INVALID_CONTENT,
|
||||||
|
"<schema id='%s' list-of='%s'> extends <schema "
|
||||||
|
"id='%s' list-of='%s'> but '%s' does not extend '%s'",
|
||||||
|
id, list_of, extends_name, extends->list_of,
|
||||||
|
list_of, extends->list_of);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
/* by default we are a list of the same thing that the schema
|
||||||
|
* we are extending is a list of (which might be nothing)
|
||||||
|
*/
|
||||||
|
list_of = extends->list_of;
|
||||||
|
}
|
||||||
|
|
||||||
if (path && !(g_str_has_prefix (path, "/") && g_str_has_suffix (path, "/")))
|
if (path && !(g_str_has_prefix (path, "/") && g_str_has_suffix (path, "/")))
|
||||||
{
|
{
|
||||||
g_set_error (error, G_MARKUP_ERROR,
|
g_set_error (error, G_MARKUP_ERROR,
|
||||||
@ -833,7 +933,8 @@ parse_state_start_schema (ParseState *state,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
state->schema_state = schema_state_new (path, gettext_domain);
|
state->schema_state = schema_state_new (path, gettext_domain,
|
||||||
|
extends, extends_name, list_of);
|
||||||
g_hash_table_insert (state->schema_table, g_strdup (id),
|
g_hash_table_insert (state->schema_table, g_strdup (id),
|
||||||
state->schema_state);
|
state->schema_state);
|
||||||
}
|
}
|
||||||
@ -900,11 +1001,14 @@ start_element (GMarkupParseContext *context,
|
|||||||
{
|
{
|
||||||
if (strcmp (element_name, "schema") == 0)
|
if (strcmp (element_name, "schema") == 0)
|
||||||
{
|
{
|
||||||
const gchar *id, *path, *gettext_domain;
|
const gchar *id, *path, *gettext_domain, *extends, *list_of;
|
||||||
if (COLLECT (STRING, "id", &id,
|
if (COLLECT (STRING, "id", &id,
|
||||||
OPTIONAL | STRING, "path", &path,
|
OPTIONAL | STRING, "path", &path,
|
||||||
OPTIONAL | STRING, "gettext-domain", &gettext_domain))
|
OPTIONAL | STRING, "gettext-domain", &gettext_domain,
|
||||||
parse_state_start_schema (state, id, path, gettext_domain, error);
|
OPTIONAL | STRING, "extends", &extends,
|
||||||
|
OPTIONAL | STRING, "list-of", &list_of))
|
||||||
|
parse_state_start_schema (state, id, path, gettext_domain,
|
||||||
|
extends, list_of, error);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -302,9 +302,18 @@ schema_tests = \
|
|||||||
schema-tests/enum-with-repeated-alias.gschema.xml \
|
schema-tests/enum-with-repeated-alias.gschema.xml \
|
||||||
schema-tests/enum-with-shadow-alias.gschema.xml \
|
schema-tests/enum-with-shadow-alias.gschema.xml \
|
||||||
schema-tests/enum.gschema.xml \
|
schema-tests/enum.gschema.xml \
|
||||||
|
schema-tests/extend-missing.gschema.xml \
|
||||||
|
schema-tests/extend-nonlist.gschema.xml \
|
||||||
|
schema-tests/extend-self.gschema.xml \
|
||||||
|
schema-tests/extend-wrong-list-indirect.gschema.xml \
|
||||||
|
schema-tests/extend-wrong-list.gschema.xml \
|
||||||
|
schema-tests/extending.gschema.xml \
|
||||||
schema-tests/from-docs.gschema.xml \
|
schema-tests/from-docs.gschema.xml \
|
||||||
schema-tests/incomplete-list.gschema.xml \
|
schema-tests/incomplete-list.gschema.xml \
|
||||||
schema-tests/invalid-path.gschema.xml \
|
schema-tests/invalid-path.gschema.xml \
|
||||||
|
schema-tests/key-in-list-indirect.gschema.xml \
|
||||||
|
schema-tests/key-in-list.gschema.xml \
|
||||||
|
schema-tests/list-of-missing.gschema.xml \
|
||||||
schema-tests/missing-quotes.gschema.xml \
|
schema-tests/missing-quotes.gschema.xml \
|
||||||
schema-tests/no-default.gschema.xml \
|
schema-tests/no-default.gschema.xml \
|
||||||
schema-tests/overflow.gschema.xml \
|
schema-tests/overflow.gschema.xml \
|
||||||
@ -320,7 +329,6 @@ schema_tests = \
|
|||||||
schema-tests/range.gschema.xml \
|
schema-tests/range.gschema.xml \
|
||||||
schema-tests/wrong-category.gschema.xml
|
schema-tests/wrong-category.gschema.xml
|
||||||
|
|
||||||
|
|
||||||
EXTRA_DIST += \
|
EXTRA_DIST += \
|
||||||
socket-common.c \
|
socket-common.c \
|
||||||
org.gtk.test.gschema \
|
org.gtk.test.gschema \
|
||||||
|
@ -92,7 +92,16 @@ static const SchemaTest tests[] = {
|
|||||||
{ "range-default-low", NULL, "*<default> is not contained in the specified range*" },
|
{ "range-default-low", NULL, "*<default> is not contained in the specified range*" },
|
||||||
{ "range-default-high", NULL, "*<default> is not contained in the specified range*" },
|
{ "range-default-high", NULL, "*<default> is not contained in the specified range*" },
|
||||||
{ "range-parse-error", NULL, "*invalid character in number*" },
|
{ "range-parse-error", NULL, "*invalid character in number*" },
|
||||||
{ "from-docs", NULL, NULL }
|
{ "from-docs", NULL, NULL },
|
||||||
|
{ "extending", NULL, NULL },
|
||||||
|
{ "extend-missing", NULL, "*extends not yet existing schema*" },
|
||||||
|
{ "extend-nonlist", NULL, "*which is not a list*" },
|
||||||
|
{ "extend-self", NULL, "*not yet existing*" },
|
||||||
|
{ "extend-wrong-list-indirect", NULL, "*'y' does not extend 'x'*" },
|
||||||
|
{ "extend-wrong-list", NULL, "*'y' does not extend 'x'*" },
|
||||||
|
{ "key-in-list-indirect", NULL, "*can not add keys to a list*" },
|
||||||
|
{ "key-in-list", NULL, "*can not add keys to a list*" },
|
||||||
|
{ "list-of-missing", NULL, "*is list of not yet existing schema*" }
|
||||||
};
|
};
|
||||||
|
|
||||||
int
|
int
|
||||||
|
3
gio/tests/schema-tests/extend-missing.gschema.xml
Normal file
3
gio/tests/schema-tests/extend-missing.gschema.xml
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
<schemalist>
|
||||||
|
<schema id='a' extends='x'/>
|
||||||
|
</schemalist>
|
4
gio/tests/schema-tests/extend-nonlist.gschema.xml
Normal file
4
gio/tests/schema-tests/extend-nonlist.gschema.xml
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
<schemalist>
|
||||||
|
<schema id='a'/> <schema id='x'/>
|
||||||
|
<schema id='b' list-of='x' extends='a'/>
|
||||||
|
</schemalist>
|
3
gio/tests/schema-tests/extend-self.gschema.xml
Normal file
3
gio/tests/schema-tests/extend-self.gschema.xml
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
<schemalist>
|
||||||
|
<schema id='a' extends='a'/>
|
||||||
|
</schemalist>
|
@ -0,0 +1,6 @@
|
|||||||
|
<schemalist>
|
||||||
|
<schema id='x'/> <schema id='y'/>
|
||||||
|
<schema id='lx' list-of='x'/>
|
||||||
|
<schema id='lx2' extends='lx'/>
|
||||||
|
<schema id='ly' extends='lx2' list-of='y'/>
|
||||||
|
</schemalist>
|
5
gio/tests/schema-tests/extend-wrong-list.gschema.xml
Normal file
5
gio/tests/schema-tests/extend-wrong-list.gschema.xml
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
<schemalist>
|
||||||
|
<schema id='x'/> <schema id='y'/>
|
||||||
|
<schema id='lx' list-of='x'/>
|
||||||
|
<schema id='ly' extends='lx' list-of='y'/>
|
||||||
|
</schemalist>
|
21
gio/tests/schema-tests/extending.gschema.xml
Normal file
21
gio/tests/schema-tests/extending.gschema.xml
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
<schemalist>
|
||||||
|
<!-- c extends b extends a -->
|
||||||
|
<schema id='a'/>
|
||||||
|
<schema id='b' extends='a'/>
|
||||||
|
<schema id='c' extends='b'/>
|
||||||
|
|
||||||
|
<!-- lists of each -->
|
||||||
|
<schema id='la' list-of='a'/>
|
||||||
|
<schema id='lb' list-of='b'/>
|
||||||
|
<schema id='lc' list-of='c'/>
|
||||||
|
|
||||||
|
<!-- extend 'la', override the list-of to 'b' -->
|
||||||
|
<schema id='lb-la' list-of='b' extends='la'/>
|
||||||
|
|
||||||
|
<!-- extend 'la', override the list-of to 'c' -->
|
||||||
|
<schema id='lc-la' list-of='c' extends='la'/>
|
||||||
|
<!-- extend 'lb', override the list-of to 'c' -->
|
||||||
|
<schema id='lc-lb' list-of='c' extends='lb'/>
|
||||||
|
<!-- extend 'lb-la', override the list-of to 'c' -->
|
||||||
|
<schema id='lc-lb-la' list-of='c' extends='lb-la'/>
|
||||||
|
</schemalist>
|
8
gio/tests/schema-tests/key-in-list-indirect.gschema.xml
Normal file
8
gio/tests/schema-tests/key-in-list-indirect.gschema.xml
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
<schemalist>
|
||||||
|
<schema id='y'/>
|
||||||
|
<schema id='x' list-of='y'/>
|
||||||
|
|
||||||
|
<schema id='z' extends='x'>
|
||||||
|
<key name='foo' type='s'/>
|
||||||
|
</schema>
|
||||||
|
</schemalist>
|
6
gio/tests/schema-tests/key-in-list.gschema.xml
Normal file
6
gio/tests/schema-tests/key-in-list.gschema.xml
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
<schemalist>
|
||||||
|
<schema id='y'/>
|
||||||
|
<schema id='x' list-of='y'>
|
||||||
|
<key name='foo' type='s'/>
|
||||||
|
</schema>
|
||||||
|
</schemalist>
|
3
gio/tests/schema-tests/list-of-missing.gschema.xml
Normal file
3
gio/tests/schema-tests/list-of-missing.gschema.xml
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
<schemalist>
|
||||||
|
<schema id='a' list-of='x'/>
|
||||||
|
</schemalist>
|
Loading…
Reference in New Issue
Block a user