mirror of
https://gitlab.freedesktop.org/pipewire/wireplumber.git
synced 2025-12-20 04:10:03 +01:00
core: change the component arguments to be WpSpaJson instead of GVariant
This allows us to pass entire JSON objects from the config file down to the modules / scripts without any conversion
This commit is contained in:
parent
d755ec4f20
commit
5c3032c064
20 changed files with 63 additions and 59 deletions
|
|
@ -31,7 +31,7 @@ WP_DEFINE_LOCAL_LOG_TOPIC ("wp-comp-loader")
|
|||
*/
|
||||
|
||||
#define WP_MODULE_INIT_SYMBOL "wireplumber__module_init"
|
||||
typedef GObject *(*WpModuleInitFunc) (WpCore *, GVariant *, GError **);
|
||||
typedef GObject *(*WpModuleInitFunc) (WpCore *, WpSpaJson *, GError **);
|
||||
|
||||
G_DEFINE_ABSTRACT_TYPE (WpComponentLoader, wp_component_loader, WP_TYPE_PLUGIN)
|
||||
|
||||
|
|
@ -47,7 +47,7 @@ wp_component_loader_class_init (WpComponentLoaderClass * klass)
|
|||
|
||||
static GObject *
|
||||
load_module (WpCore * core, const gchar * module_name,
|
||||
GVariant * args, GError ** error)
|
||||
WpSpaJson * args, GError ** error)
|
||||
{
|
||||
g_autofree gchar *module_path = NULL;
|
||||
GModule *gmodule;
|
||||
|
|
@ -99,7 +99,7 @@ wp_component_loader_find (WpCore * core, const gchar * type)
|
|||
|
||||
static void
|
||||
wp_component_loader_load (WpComponentLoader * self, const gchar * component,
|
||||
const gchar * type, GVariant * args, GAsyncReadyCallback callback,
|
||||
const gchar * type, WpSpaJson * args, GAsyncReadyCallback callback,
|
||||
gpointer data)
|
||||
{
|
||||
g_return_if_fail (WP_IS_COMPONENT_LOADER (self));
|
||||
|
|
@ -132,17 +132,16 @@ on_object_loaded (WpObject *object, GAsyncResult *res, gpointer data)
|
|||
* \param self the core
|
||||
* \param component the module name or file name
|
||||
* \param type the type of the component
|
||||
* \param args (transfer floating)(nullable): additional arguments for the component,
|
||||
* usually a dict or a string
|
||||
* \param args (transfer none)(nullable): additional arguments for the component,
|
||||
* expected to be a JSON object
|
||||
* \param callback (scope async): the callback to call when the operation is done
|
||||
* \param data (closure): data to pass to \a callback
|
||||
*/
|
||||
void
|
||||
wp_core_load_component (WpCore * self, const gchar * component,
|
||||
const gchar * type, GVariant * args, GAsyncReadyCallback callback,
|
||||
const gchar * type, WpSpaJson * args, GAsyncReadyCallback callback,
|
||||
gpointer data)
|
||||
{
|
||||
g_autoptr (GVariant) args_ref = args ? g_variant_ref_sink (args) : NULL;
|
||||
g_autoptr (GTask) task = NULL;
|
||||
g_autoptr (WpComponentLoader) c = NULL;
|
||||
|
||||
|
|
@ -153,7 +152,7 @@ wp_core_load_component (WpCore * self, const gchar * component,
|
|||
g_autoptr (GObject) o = NULL;
|
||||
|
||||
/* load Module */
|
||||
o = load_module (self, component, args_ref, &error);
|
||||
o = load_module (self, component, args, &error);
|
||||
if (!o) {
|
||||
g_task_return_error (task, g_steal_pointer (&error));
|
||||
return;
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@
|
|||
#define __WIREPLUMBER_COMPONENT_LOADER_H__
|
||||
|
||||
#include "plugin.h"
|
||||
#include "spa-json.h"
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
|
|
@ -29,7 +30,7 @@ struct _WpComponentLoaderClass
|
|||
gboolean (*supports_type) (WpComponentLoader * self, const gchar * type);
|
||||
|
||||
void (*load) (WpComponentLoader * self, const gchar * component,
|
||||
const gchar * type, GVariant * args, GAsyncReadyCallback callback,
|
||||
const gchar * type, WpSpaJson * args, GAsyncReadyCallback callback,
|
||||
gpointer data);
|
||||
|
||||
/*< private >*/
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@
|
|||
#include <gio/gio.h>
|
||||
#include "defs.h"
|
||||
#include "properties.h"
|
||||
#include "spa-json.h"
|
||||
|
||||
G_BEGIN_DECLS
|
||||
|
||||
|
|
@ -49,7 +50,7 @@ gchar *wp_core_get_vm_type (WpCore *self);
|
|||
|
||||
WP_API
|
||||
void wp_core_load_component (WpCore * self, const gchar * component,
|
||||
const gchar * type, GVariant * args, GAsyncReadyCallback callback,
|
||||
const gchar * type, WpSpaJson * args, GAsyncReadyCallback callback,
|
||||
gpointer data);
|
||||
|
||||
WP_API
|
||||
|
|
|
|||
|
|
@ -307,7 +307,7 @@ wp_default_nodes_api_class_init (WpDefaultNodesApiClass * klass)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (g_object_new (wp_default_nodes_api_get_type (),
|
||||
"name", "default-nodes-api",
|
||||
|
|
|
|||
|
|
@ -204,7 +204,7 @@ wp_file_monitor_api_class_init (WpFileMonitorApiClass * klass)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (g_object_new (wp_file_monitor_api_get_type (),
|
||||
"name", "file-monitor-api",
|
||||
|
|
|
|||
|
|
@ -134,7 +134,7 @@ wp_logind_class_init (WpLogindClass * klass)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (g_object_new (wp_logind_get_type (),
|
||||
"name", NAME,
|
||||
|
|
|
|||
|
|
@ -173,7 +173,7 @@ on_script_loaded (WpObject *object, GAsyncResult *res, gpointer data)
|
|||
|
||||
static void
|
||||
wp_lua_scripting_plugin_load (WpComponentLoader * cl, const gchar * component,
|
||||
const gchar * type, GVariant * args, GAsyncReadyCallback callback,
|
||||
const gchar * type, WpSpaJson * args, GAsyncReadyCallback callback,
|
||||
gpointer data)
|
||||
{
|
||||
WpLuaScriptingPlugin * self = WP_LUA_SCRIPTING_PLUGIN (cl);
|
||||
|
|
@ -238,7 +238,7 @@ wp_lua_scripting_plugin_class_init (WpLuaScriptingPluginClass * klass)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (g_object_new (wp_lua_scripting_plugin_get_type (),
|
||||
"name", "lua-scripting",
|
||||
|
|
|
|||
|
|
@ -29,7 +29,7 @@ struct _WpLuaScript
|
|||
|
||||
lua_State *L;
|
||||
gchar *filename;
|
||||
GVariant *args;
|
||||
WpSpaJson *args;
|
||||
};
|
||||
|
||||
enum {
|
||||
|
|
@ -64,7 +64,7 @@ wp_lua_script_finalize (GObject * object)
|
|||
wp_lua_script_cleanup (self);
|
||||
g_clear_pointer (&self->L, wplua_unref);
|
||||
g_clear_pointer (&self->filename, g_free);
|
||||
g_clear_pointer (&self->args, g_variant_unref);
|
||||
g_clear_pointer (&self->args, wp_spa_json_unref);
|
||||
|
||||
G_OBJECT_CLASS (wp_lua_script_parent_class)->finalize (object);
|
||||
}
|
||||
|
|
@ -86,7 +86,7 @@ wp_lua_script_set_property (GObject * object, guint property_id,
|
|||
self->filename = g_value_dup_string (value);
|
||||
break;
|
||||
case PROP_ARGUMENTS:
|
||||
self->args = g_value_dup_variant (value);
|
||||
self->args = g_value_dup_boxed (value);
|
||||
break;
|
||||
default:
|
||||
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
|
||||
|
|
@ -231,7 +231,7 @@ wp_lua_script_enable (WpPlugin * plugin, WpTransition * transition)
|
|||
|
||||
/* push script arguments */
|
||||
if (self->args) {
|
||||
wplua_gvariant_to_lua (self->L, self->args);
|
||||
wplua_pushboxed (self->L, WP_TYPE_SPA_JSON, wp_spa_json_ref (self->args));
|
||||
nargs++;
|
||||
}
|
||||
|
||||
|
|
@ -282,7 +282,7 @@ wp_lua_script_class_init (WpLuaScriptClass * klass)
|
|||
G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_STRINGS));
|
||||
|
||||
g_object_class_install_property (object_class, PROP_ARGUMENTS,
|
||||
g_param_spec_variant ("arguments", "arguments", "arguments",
|
||||
G_VARIANT_TYPE_VARDICT, NULL,
|
||||
g_param_spec_boxed ("arguments", "arguments", "arguments",
|
||||
WP_TYPE_SPA_JSON,
|
||||
G_PARAM_WRITABLE | G_PARAM_CONSTRUCT_ONLY | G_PARAM_STATIC_STRINGS));
|
||||
}
|
||||
|
|
|
|||
|
|
@ -30,6 +30,7 @@ _wplua_gboxed___index (lua_State *L)
|
|||
"expected userdata storing GValue<GBoxed>");
|
||||
GValue *obj_v = lua_touserdata (L, 1);
|
||||
const gchar *key = luaL_checkstring (L, 2);
|
||||
GType type = G_VALUE_TYPE (obj_v);
|
||||
lua_CFunction func = NULL;
|
||||
GHashTable *vtables;
|
||||
|
||||
|
|
@ -39,15 +40,15 @@ _wplua_gboxed___index (lua_State *L)
|
|||
lua_pop (L, 1);
|
||||
|
||||
/* search in registered vtables */
|
||||
if (!func) {
|
||||
GType type = G_VALUE_TYPE (obj_v);
|
||||
while (!func && type) {
|
||||
luaL_Reg *reg = g_hash_table_lookup (vtables, GUINT_TO_POINTER (type));
|
||||
func = find_method_in_luaL_Reg (reg, key);
|
||||
type = g_type_parent (type);
|
||||
}
|
||||
while (!func && type) {
|
||||
luaL_Reg *reg = g_hash_table_lookup (vtables, GUINT_TO_POINTER (type));
|
||||
func = find_method_in_luaL_Reg (reg, key);
|
||||
type = g_type_parent (type);
|
||||
}
|
||||
|
||||
wp_trace_boxed (type, g_value_get_boxed (obj_v),
|
||||
"indexing GBoxed, looking for '%s', found: %p", key, func);
|
||||
|
||||
if (func) {
|
||||
lua_pushcfunction (L, func);
|
||||
return 1;
|
||||
|
|
|
|||
|
|
@ -617,7 +617,7 @@ wp_mixer_api_class_init (WpMixerApiClass * klass)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (g_object_new (wp_mixer_api_get_type (),
|
||||
"name", "mixer-api",
|
||||
|
|
|
|||
|
|
@ -305,7 +305,7 @@ wp_portal_permissionstore_plugin_class_init (
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (g_object_new (
|
||||
wp_portal_permissionstore_plugin_get_type(),
|
||||
|
|
|
|||
|
|
@ -267,7 +267,7 @@ wp_reserve_device_plugin_class_init (WpReserveDevicePluginClass * klass)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (g_object_new (wp_reserve_device_plugin_get_type (),
|
||||
"name", "reserve-device",
|
||||
|
|
|
|||
|
|
@ -339,15 +339,15 @@ wp_settings_plugin_class_init (WpSettingsPluginClass * klass)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
const gchar *metadata_name = "sm-settings";
|
||||
g_autofree gchar *metadata_name = NULL;
|
||||
if (args)
|
||||
metadata_name = g_variant_get_string (args, NULL);
|
||||
wp_spa_json_object_get (args, "metadata-name", "s", &metadata_name, NULL);
|
||||
|
||||
return G_OBJECT (g_object_new (wp_settings_plugin_get_type (),
|
||||
"name", "settings",
|
||||
"core", core,
|
||||
"metadata-name", metadata_name,
|
||||
"metadata-name", metadata_name ? metadata_name : "sm-settings",
|
||||
NULL));
|
||||
}
|
||||
|
|
|
|||
|
|
@ -780,7 +780,7 @@ si_audio_adapter_linkable_init (WpSiLinkableInterface * iface)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (wp_si_factory_new_simple (SI_FACTORY_NAME,
|
||||
si_audio_adapter_get_type ()));
|
||||
|
|
|
|||
|
|
@ -358,7 +358,7 @@ si_audio_virtual_adapter_init (WpSiAdapterInterface * iface)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (wp_si_factory_new_simple (SI_FACTORY_NAME,
|
||||
si_audio_virtual_get_type ()));
|
||||
|
|
|
|||
|
|
@ -222,7 +222,7 @@ si_node_linkable_init (WpSiLinkableInterface * iface)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (wp_si_factory_new_simple (SI_FACTORY_NAME,
|
||||
si_node_get_type ()));
|
||||
|
|
|
|||
|
|
@ -778,7 +778,7 @@ si_standard_link_link_init (WpSiLinkInterface * iface)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (wp_si_factory_new_simple (SI_FACTORY_NAME,
|
||||
si_standard_link_get_type ()));
|
||||
|
|
|
|||
|
|
@ -452,7 +452,7 @@ wp_standard_event_source_class_init (WpStandardEventSourceClass * klass)
|
|||
}
|
||||
|
||||
WP_PLUGIN_EXPORT GObject *
|
||||
wireplumber__module_init (WpCore * core, GVariant * args, GError ** error)
|
||||
wireplumber__module_init (WpCore * core, WpSpaJson * args, GError ** error)
|
||||
{
|
||||
return G_OBJECT (g_object_new (wp_standard_event_source_get_type (),
|
||||
"name", "standard-event-source",
|
||||
|
|
|
|||
|
|
@ -27,8 +27,8 @@ enum WpExitCode
|
|||
};
|
||||
|
||||
static gchar * exec_script = NULL;
|
||||
static GVariantBuilder exec_args_b =
|
||||
G_VARIANT_BUILDER_INIT (G_VARIANT_TYPE_VARDICT);
|
||||
static gchar *exec_args_s = NULL;
|
||||
static WpSpaJson *exec_args = NULL;
|
||||
|
||||
static gboolean
|
||||
parse_exec_script_arg (const gchar *option_name, const gchar *value,
|
||||
|
|
@ -40,16 +40,17 @@ parse_exec_script_arg (const gchar *option_name, const gchar *value,
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
g_auto(GStrv) tokens = g_strsplit (value, "=", 2);
|
||||
if (!tokens[0] || *g_strstrip (tokens[0]) == '\0') {
|
||||
g_set_error (error, WP_DOMAIN_DAEMON, WP_EXIT_USAGE,
|
||||
"invalid script argument '%s'; must be in key=value format", value);
|
||||
return FALSE;
|
||||
/* the second argument is a json object with script arguments */
|
||||
if (!exec_args) {
|
||||
exec_args_s = g_strdup (value);
|
||||
exec_args = wp_spa_json_new_from_string (exec_args_s);
|
||||
if (!exec_args || !wp_spa_json_is_object (exec_args)) {
|
||||
g_set_error (error, WP_DOMAIN_DAEMON, WP_EXIT_USAGE,
|
||||
"script argument must be a JSON object");
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
g_variant_builder_add (&exec_args_b, "{sv}", tokens[0], tokens[1] ?
|
||||
g_variant_new_string (g_strstrip (tokens[1])) :
|
||||
g_variant_new_boolean (TRUE));
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
|
@ -146,8 +147,7 @@ wp_init_transition_execute_step (WpTransition * transition, guint step)
|
|||
}
|
||||
|
||||
case STEP_ACTIVATE_SCRIPT: {
|
||||
GVariant *args = g_variant_builder_end (&exec_args_b);
|
||||
wp_core_load_component (core, exec_script, "script/lua", args,
|
||||
wp_core_load_component (core, exec_script, "script/lua", exec_args,
|
||||
(GAsyncReadyCallback) on_plugin_loaded, self);
|
||||
break;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,21 +10,23 @@
|
|||
-- This is an example of an interactive script
|
||||
--
|
||||
-- Execute with:
|
||||
-- wpexec ./interactive.lua option1=value1 option2=value2 ...
|
||||
-- wpexec ./interactive.lua '{ option1 = "value1" , option2 = "value2" }' ...
|
||||
-- or:
|
||||
-- ./interactive.lua option1=value1 option2=value2
|
||||
-- ./interactive.lua '{ option1 = "value1" , option2 = "value2" }'
|
||||
-----------------------------------------------------------------------------
|
||||
|
||||
--
|
||||
-- Collects arguments passed in from the command line
|
||||
-- Assuming option1=value1 option2=value2 were passed, this will be a table
|
||||
-- like this: { ["option1"] = "value1", ["option2"] = "value2" }
|
||||
-- Assuming '{ option1 = "value1" , option2 = "value2" }' were passed,
|
||||
-- this will be a table like this:
|
||||
-- { ["option1"] = "value1", ["option2"] = "value2" }
|
||||
--
|
||||
local argv = ...
|
||||
if argv then
|
||||
argv = argv:parse()
|
||||
|
||||
print ("Command-line arguments:")
|
||||
for k, v in pairs(argv) do
|
||||
print ("\t" .. k .. ": " .. v)
|
||||
print ("Command-line arguments:")
|
||||
Debug.dump_table (argv)
|
||||
end
|
||||
|
||||
--
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue