diff options
-rwxr-xr-x | mate-conf/mate-conf-import | 310 |
1 files changed, 310 insertions, 0 deletions
diff --git a/mate-conf/mate-conf-import b/mate-conf/mate-conf-import new file mode 100755 index 0000000..decce4a --- /dev/null +++ b/mate-conf/mate-conf-import @@ -0,0 +1,310 @@ +#!/usr/bin/env python +# +# Copyright (c) 2013 Stefano Karapetsas +# +# This program is free software; you can redistribute it and/or +# modify it under the terms of the GNU Lesser General Public License +# as published by the Free Software Foundation; either version 2 +# of the License, or (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public +# License along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, +# USA. +# +# Authors: Stefano Karapetsas <[email protected]> + +import glob +import optparse +import os +import sys + +# to read MateConf files +import xml.etree.ElementTree as ElementTree + +# to write GSettings +import gi +gi.require_version("Gtk", "2.0") +from gi.repository import Gtk +from gi.repository import GLib +from gi.repository import Gio + +# command options +parser = optparse.OptionParser() +parser.add_option("-d", "--debug", dest="debug", action="store_true", help="enable debug messages") +parser.add_option("-f", "--force", dest="force", action="store_true", help="force migration of settings") +(options, args) = parser.parse_args() + +# print a message only if debug option is enabled +def debug_message(*argv): + args = [] + for arg in argv: + args.append(str(arg)) + if options.debug: + print " ".join(args) + +# get a mateconf string list +def mateconf_get_string_list(root, key): + for child in root: + if child.attrib['name'] == key: + if child.attrib["type"] == "list": + if child.attrib["ltype"] == "string": + if len(list(child)) > 0: + strv = [] + for ch in child: + for li in ch: + strv.append(li.text) + return strv + else: + return [] + return None + +def gsettings_id(id): + return id.replace("_", "-") + +mateconf_user_path = os.path.dirname(os.path.join(GLib.get_home_dir(), ".mateconf/")) +if not os.path.exists(mateconf_user_path): + #FIXME save key in GSettings + debug_message(mateconf_user_path, "not found!") + sys.exit(0) + +#FIXME check GSettings key +dialog = Gtk.MessageDialog (None, + Gtk.DialogFlags.MODAL, + Gtk.MessageType.QUESTION, + Gtk.ButtonsType.YES_NO, + "Migrate settings from MATE 1.4?") +res = dialog.run() +if res != Gtk.ResponseType.YES: + sys.exit(0) +dialog.destroy() + +# load .convert files list from MateConf folder +convert_files = glob.glob("/usr/share/MateConf/gsettings/*") + +no_background = False +for convert_file in convert_files: + + # load .convert file + keyfile = GLib.KeyFile.new() + GLib.KeyFile.load_from_file(keyfile, convert_file, 0) + groups = GLib.KeyFile.get_groups(keyfile) + + # iter GSettings schemas + for group in groups[0]: + + # each group is a GSettings schema + gsettings_schema = group + keys = GLib.KeyFile.get_keys(keyfile, group); + settings = Gio.Settings.new(gsettings_schema) + + # delay settings to save them only once + settings.delay() + + # iter GSettings keys + for gsettings_key in keys[0]: + + # get mateconf xml file, + mateconf_fullkey = GLib.KeyFile.get_string(keyfile, group, gsettings_key) + mateconf_path = os.path.dirname(os.path.join(mateconf_user_path, mateconf_fullkey[1:])) + mateconf_file = os.path.join(mateconf_path, "%mateconf.xml") + mateconf_key = os.path.basename(mateconf_fullkey) + + # if user has custom mateconf + if os.path.exists(mateconf_file): + + try: + tree = ElementTree.parse(mateconf_file) + root = tree.getroot() + except: + continue + + for child in root: + # if the key exists, the user has a custom value + if child.attrib['name'] == mateconf_key: + + # boolean + if child.attrib["type"] == "bool": + if child.attrib["value"] == "true": + debug_message(gsettings_schema, gsettings_key, True) + settings.set_boolean(gsettings_key, True) + else: + debug_message(gsettings_schema, gsettings_key, False) + settings.set_boolean(gsettings_key, False) + + # int + elif child.attrib["type"] == "int": + debug_message(gsettings_schema, gsettings_key, int(child.attrib["value"])) + settings.set_int(gsettings_key, int(child.attrib["value"])) + + # string + elif child.attrib["type"] == "string": + + # hack for background + if gsettings_schema == "org.mate.background" and gsettings_key == "picture-filename": + # check if the background exists before apply it + if not os.path.exists(child[0].text): + no_background = True + continue + if no_background and gsettings_schema == "org.mate.background": + continue + + debug_message(gsettings_schema, gsettings_key, child[0].text) + settings.set_string(gsettings_key, child[0].text) + + # list + elif child.attrib["type"] == "list": + + # list of strings + if child.attrib["ltype"] == "string": + + if len(list(child)) > 0: + strv = [] + for ch in child: + for li in ch: + strv.append(li.text) + debug_message(gsettings_schema, gsettings_key, strv) + settings.set_strv(gsettings_key, strv) + else: + debug_message(gsettings_schema, gsettings_key, "[]") + settings.set_strv(gsettings_key, []) + else: + debug_message("Unknown list type", child.attrib["ltype"]) + + else: + debug_message("Unknown type", child.attrib["type"]) + + settings.apply() + +# ugly hack to migrate panel layout +mateconf_panel_file = os.path.join(mateconf_user_path, "apps/panel/general", "%mateconf.xml") +if os.path.exists(mateconf_panel_file): + + # load list of panels + tree = ElementTree.parse(mateconf_panel_file) + root = tree.getroot() + + # old lists + toplevels = mateconf_get_string_list (root, "toplevel_id_list") + objects = mateconf_get_string_list (root, "object_id_list") + applets = mateconf_get_string_list (root, "applet_id_list") + + panel_settings = Gio.Settings.new("org.mate.panel") + panel_settings.delay() + + # new lists (applets are together with objects in 1.6) + new_toplevels = [] + new_objects = [] + + # import objects + for obj in objects: + debug_message("object", obj) + mateconf_obj_file = os.path.join(mateconf_user_path, "apps/panel/objects", obj, "%mateconf.xml") + obj_tree = ElementTree.parse(mateconf_obj_file) + obj_root = obj_tree.getroot() + obj_id = gsettings_id(obj) + obj_settings = Gio.Settings.new_with_path("org.mate.panel.object", "/org/mate/panel/objects/%s/" % obj_id) + new_objects.append(obj_id) + + for child in obj_root: + if child.attrib["name"] == "toplevel_id": + obj_settings.set_string("toplevel-id", gsettings_id(child[0].text)) + elif child.attrib["name"] == "object_type": + obj_type = child[0].text + # changed types + if obj_type == "launcher-object": + obj_type = "launcher" + obj_settings.set_string("object-type", obj_type) + elif "type" in child.attrib: + name = gsettings_id(child.attrib["name"]) + if child.attrib["type"] == "bool": + if child.attrib["value"] == "true": + obj_settings.set_boolean(name, True) + else: + obj_settings.set_boolean(name, False) + elif child.attrib["type"] == "int": + obj_settings.set_int(name, int(child.attrib["value"])) + elif child.attrib["type"] == "string": + obj_settings.set_string(name, child[0].text) + + # import applets + for app in applets: + debug_message("applet", app) + mateconf_app_file = os.path.join(mateconf_user_path, "apps/panel/applets", app, "%mateconf.xml") + app_tree = ElementTree.parse(mateconf_app_file) + app_root = app_tree.getroot() + app_id = gsettings_id(app) + app_settings = Gio.Settings.new_with_path("org.mate.panel.object", "/org/mate/panel/objects/%s/" % app_id) + new_objects.append(app_id) + + for child in app_root: + if child.attrib["name"] == "toplevel_id": + app_settings.set_string("toplevel-id", gsettings_id(child[0].text)) + elif child.attrib["name"] == "object_type": + app_type = child[0].text + if app_type == "external-applet": + app_type = "applet" + app_settings.set_string("object-type", app_type) + elif child.attrib["name"] == "applet_iid": + applet_iid = child[0].text + # changed iids + if applet_iid == "OAFIID:SensorsApplet": + applet_iid = "SensorsAppletFactory::SensorsApplet" + elif applet_iid == "OAFIID:MATE_NetspeedApplet": + applet_iid = "NetspeedAppletFactory::NetspeedApplet" + app_settings.set_string("applet-iid", applet_iid) + elif "type" in child.attrib: + name = gsettings_id(child.attrib["name"]) + if child.attrib["type"] == "bool": + if child.attrib["value"] == "true": + app_settings.set_boolean(name, True) + else: + app_settings.set_boolean(name, False) + elif child.attrib["type"] == "int": + app_settings.set_int(name, int(child.attrib["value"])) + elif child.attrib["type"] == "string": + app_settings.set_string(name, child[0].text) + + # import panels + for toplevel in toplevels: + debug_message("toplevel", toplevel) + mateconf_toplevel_file = os.path.join(mateconf_user_path, "apps/panel/toplevels", toplevel, "%mateconf.xml") + toplevel_tree = ElementTree.parse(mateconf_toplevel_file) + toplevel_root = toplevel_tree.getroot() + toplevel_id = gsettings_id(toplevel) + toplevel_settings = Gio.Settings.new_with_path("org.mate.panel.toplevel", "/org/mate/panel/toplevels/%s/" % toplevel_id) + new_toplevels.append(toplevel_id) + + for child in toplevel_root: + if "type" in child.attrib: + name = gsettings_id(child.attrib["name"]) + if child.attrib["type"] == "bool": + if child.attrib["value"] == "true": + toplevel_settings.set_boolean(name, True) + else: + toplevel_settings.set_boolean(name, False) + elif child.attrib["type"] == "int": + toplevel_settings.set_int(name, int(child.attrib["value"])) + elif child.attrib["type"] == "string": + toplevel_settings.set_string(name, child[0].text) + + # set new toplevels and objects + panel_settings.set_strv("toplevel-id-list", new_toplevels) + panel_settings.set_strv("object-id-list", new_objects) + + # apply settings! + panel_settings.apply() + +# success! +dialog = Gtk.MessageDialog (None, + Gtk.DialogFlags.MODAL, + Gtk.MessageType.INFO, + Gtk.ButtonsType.OK, + "MATE 1.4 settings migration completed!") +dialog.run() +dialog.destroy() |