Added CORBA interface to the archiver
This commit is contained in:
parent
7c531bc29e
commit
4e6a3b89d6
28 changed files with 2258 additions and 1121 deletions
|
@ -1,4 +1,4 @@
|
|||
SUBDIRS = archiver capplets control-center po intl
|
||||
SUBDIRS = archiver capplets control-center idl po intl
|
||||
#I removed the root-manager for now
|
||||
#
|
||||
# it generated this error :
|
||||
|
|
|
@ -8,7 +8,7 @@
|
|||
<oaf_attribute name="name" type="string" value="XML Database Moniker factory"/>
|
||||
</oaf_server>
|
||||
|
||||
<oaf_server iid="OAFIID:Bonobo_Moniker_archiver" type="factory"
|
||||
<oaf_server iid="OAFIID:Bonobo_Moniker_archiverdb" type="factory"
|
||||
location="OAFIID:Bonobo_Moniker_archiver_Factory">
|
||||
<oaf_attribute name="repo_ids" type="stringv">
|
||||
<item value="IDL:Bonobo/Moniker:1.0"/>
|
||||
|
@ -16,7 +16,19 @@
|
|||
</oaf_attribute>
|
||||
<oaf_attribute name="name" type="string" value="XML Database Moniker with archiver interface"/>
|
||||
<oaf_attribute name="bonobo:moniker" type="stringv">
|
||||
<item value="archiver:"/>
|
||||
<item value="archiverdb:"/>
|
||||
</oaf_attribute>
|
||||
</oaf_server>
|
||||
|
||||
<oaf_server iid="OAFIID:Bonobo_Moniker_archive" type="factory"
|
||||
location="OAFIID:Bonobo_Moniker_archiver_Factory">
|
||||
<oaf_attribute name="repo_ids" type="stringv">
|
||||
<item value="IDL:Bonobo/Moniker:1.0"/>
|
||||
<item value="IDL:Bonobo/Unknown:1.0"/>
|
||||
</oaf_attribute>
|
||||
<oaf_attribute name="name" type="string" value="XML archiver interface"/>
|
||||
<oaf_attribute name="bonobo:moniker" type="stringv">
|
||||
<item value="archive:"/>
|
||||
</oaf_attribute>
|
||||
</oaf_server>
|
||||
|
||||
|
|
|
@ -1,3 +1,13 @@
|
|||
2001-08-17 Bradford Hovinen <hovinen@ximian.com>
|
||||
|
||||
* all: Added CORBA interface for the archiver
|
||||
* config-archiver.c: Ported to new CORBA interface
|
||||
|
||||
2001-08-20 Bradford Hovinen <hovinen@ximian.com>
|
||||
|
||||
* location.c (load_metadata_file): Support placing the location's
|
||||
label in the metadata file
|
||||
|
||||
2001-08-03 Bradford Hovinen <hovinen@ximian.com>
|
||||
|
||||
* config-log.c (load_log_entry): Return NULL if fgets returns NULL
|
||||
|
|
|
@ -20,39 +20,35 @@ INCLUDES = \
|
|||
@ARCHIVER_CFLAGS@ \
|
||||
@MONIKER_CFLAGS@
|
||||
|
||||
if MONIKER_ENABLE
|
||||
BONOBO_MONIKER_ARCHIVER_BIN=bonobo-moniker-archiver
|
||||
else
|
||||
BONOBO_MONIKER_ARCHIVER_BIN=
|
||||
endif
|
||||
CORBA_SOURCE = \
|
||||
ConfigArchiver.h \
|
||||
ConfigArchiver-common.c \
|
||||
ConfigArchiver-stubs.c \
|
||||
ConfigArchiver-skels.c
|
||||
|
||||
bin_PROGRAMS = $(BONOBO_MONIKER_ARCHIVER_BIN) config-archiver
|
||||
idl_flags = `gnome-config --cflags idl`
|
||||
|
||||
$(CORBA_SOURCE): $(top_srcdir)/idl/ConfigArchiver.idl
|
||||
orbit-idl $(top_srcdir)/idl/ConfigArchiver.idl -I$(top_srcdir)/idl $(idl_flags)
|
||||
|
||||
bin_PROGRAMS = bonobo-moniker-archiver config-archiver
|
||||
|
||||
lib_LTLIBRARIES = libconfig_archiver.la
|
||||
|
||||
libconfig_archiver_la_SOURCES = \
|
||||
archive.c archive.h \
|
||||
location.c location.h \
|
||||
config-log.c config-log.h \
|
||||
backend-list.c backend-list.h \
|
||||
cluster.c cluster.h \
|
||||
cluster-location.c cluster-location.h \
|
||||
util.c util.h
|
||||
util.c util.h \
|
||||
archiver-client.c \
|
||||
$(CORBA_SOURCE)
|
||||
|
||||
libconfig_archiver_la_LIBADD = \
|
||||
@GNOME_XML_LIBS@
|
||||
|
||||
include_HEADERS = \
|
||||
archive.h \
|
||||
location.h \
|
||||
config-log.h \
|
||||
backend-list.h \
|
||||
cluster.h \
|
||||
cluster-location.h \
|
||||
util.h
|
||||
ConfigArchiver.h \
|
||||
archiver-client.h
|
||||
|
||||
config_archiver_SOURCES = \
|
||||
main.c
|
||||
config-archiver.c
|
||||
|
||||
config_archiver_LDADD = \
|
||||
$(GNOME_LIBDIR) \
|
||||
|
@ -87,9 +83,14 @@ Bonobo_Moniker_archiver.oaf : $(srcdir)/Bonobo_Moniker_archiver.oaf.in $(top_bui
|
|||
clean-local:
|
||||
-rm -f $(OAF_FILES)
|
||||
|
||||
bonobo_moniker_archiver_SOURCES = \
|
||||
bonobo-config-archiver.c \
|
||||
bonobo-config-archiver.h \
|
||||
bonobo_moniker_archiver_SOURCES = \
|
||||
bonobo-config-archiver.c bonobo-config-archiver.h \
|
||||
archive.c archive.h \
|
||||
location.c location.h \
|
||||
config-log.c config-log.h \
|
||||
backend-list.c backend-list.h \
|
||||
cluster.c cluster.h \
|
||||
cluster-location.c cluster-location.h \
|
||||
bonobo-moniker-archiver.c
|
||||
|
||||
bonobo_moniker_archiver_LDADD = @MONIKER_LIBS@ libconfig_archiver.la
|
||||
|
|
|
@ -35,9 +35,6 @@
|
|||
#include "archive.h"
|
||||
#include "util.h"
|
||||
|
||||
typedef struct _GRealTree GRealTree;
|
||||
typedef struct _GTreeNode GTreeNode;
|
||||
|
||||
typedef struct _foreach_t foreach_t;
|
||||
|
||||
struct _foreach_t
|
||||
|
@ -50,15 +47,14 @@ struct _foreach_t
|
|||
|
||||
static GtkObjectClass *parent_class;
|
||||
|
||||
static Archive *user_archive;
|
||||
static Archive *global_archive;
|
||||
|
||||
enum {
|
||||
ARG_0,
|
||||
ARG_PREFIX,
|
||||
ARG_IS_GLOBAL
|
||||
};
|
||||
|
||||
#define ARCHIVE_FROM_SERVANT(servant) (ARCHIVE (bonobo_object_from_servant (servant)))
|
||||
|
||||
static void archive_init (Archive *archive);
|
||||
static void archive_class_init (ArchiveClass *klass);
|
||||
|
||||
|
@ -74,30 +70,129 @@ static void archive_get_arg (GtkObject *object,
|
|||
|
||||
static void load_all_locations (Archive *archive);
|
||||
|
||||
guint
|
||||
archive_get_type (void)
|
||||
/* CORBA interface methods */
|
||||
|
||||
static ConfigArchiver_Location
|
||||
impl_ConfigArchiver_Archive_getLocation (PortableServer_Servant servant,
|
||||
const CORBA_char *locid,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
static guint archive_type;
|
||||
|
||||
if (!archive_type) {
|
||||
GtkTypeInfo archive_info = {
|
||||
"Archive",
|
||||
sizeof (Archive),
|
||||
sizeof (ArchiveClass),
|
||||
(GtkClassInitFunc) archive_class_init,
|
||||
(GtkObjectInitFunc) archive_init,
|
||||
(GtkArgSetFunc) NULL,
|
||||
(GtkArgGetFunc) NULL
|
||||
};
|
||||
|
||||
archive_type =
|
||||
gtk_type_unique (gtk_object_get_type (),
|
||||
&archive_info);
|
||||
}
|
||||
|
||||
return archive_type;
|
||||
return CORBA_Object_duplicate (BONOBO_OBJREF (archive_get_location (ARCHIVE_FROM_SERVANT (servant), locid)), ev);
|
||||
}
|
||||
|
||||
static ConfigArchiver_Location
|
||||
impl_ConfigArchiver_Archive_createLocation (PortableServer_Servant servant,
|
||||
const CORBA_char *locid,
|
||||
const CORBA_char *label,
|
||||
const ConfigArchiver_Location parent_ref,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
Location *loc;
|
||||
|
||||
loc = archive_create_location (ARCHIVE_FROM_SERVANT (servant), locid, label,
|
||||
LOCATION (bonobo_object_from_servant (parent_ref)));
|
||||
|
||||
return bonobo_object_dup_ref (BONOBO_OBJREF (loc), ev);
|
||||
}
|
||||
|
||||
static void
|
||||
build_list_cb (Archive *archive, Location *location, GList **list)
|
||||
{
|
||||
*list = g_list_prepend (*list, bonobo_object_dup_ref (BONOBO_OBJREF (location), NULL));
|
||||
}
|
||||
|
||||
static ConfigArchiver_LocationSeq *
|
||||
impl_ConfigArchiver_Archive_getChildLocations (PortableServer_Servant servant,
|
||||
ConfigArchiver_Location location_ref,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
ConfigArchiver_LocationSeq *ret;
|
||||
Archive *archive;
|
||||
Location *location;
|
||||
GList *locs = NULL, *tmp;
|
||||
guint i = 0;
|
||||
|
||||
archive = ARCHIVE_FROM_SERVANT (servant);
|
||||
|
||||
if (location_ref == CORBA_OBJECT_NIL)
|
||||
location = NULL;
|
||||
else
|
||||
location = LOCATION (bonobo_object_from_servant (location_ref->servant));
|
||||
|
||||
archive_foreach_child_location (archive, (LocationCB) build_list_cb, location, &locs);
|
||||
|
||||
ret = ConfigArchiver_LocationSeq__alloc ();
|
||||
ret->_length = g_list_length (locs);
|
||||
ret->_buffer = CORBA_sequence_ConfigArchiver_Location_allocbuf (ret->_length);
|
||||
|
||||
for (tmp = locs; tmp != NULL; tmp = tmp->next)
|
||||
ret->_buffer[i++] = tmp->data;
|
||||
|
||||
g_list_free (locs);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static CORBA_char *
|
||||
impl_ConfigArchiver_Archive__get_prefix (PortableServer_Servant servant,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
return CORBA_string_dup (ARCHIVE_FROM_SERVANT (servant)->prefix);
|
||||
}
|
||||
|
||||
static CORBA_boolean
|
||||
impl_ConfigArchiver_Archive__get_isGlobal (PortableServer_Servant servant,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
return ARCHIVE_FROM_SERVANT (servant)->is_global;
|
||||
}
|
||||
|
||||
static ConfigArchiver_BackendList
|
||||
impl_ConfigArchiver_Archive__get_backendList (PortableServer_Servant servant,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
return bonobo_object_dup_ref (BONOBO_OBJREF (ARCHIVE_FROM_SERVANT (servant)->backend_list), ev);
|
||||
}
|
||||
|
||||
static ConfigArchiver_Location
|
||||
impl_ConfigArchiver_Archive__get_currentLocation (PortableServer_Servant servant,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
return CORBA_Object_duplicate (BONOBO_OBJREF (archive_get_current_location (ARCHIVE_FROM_SERVANT (servant))), ev);
|
||||
}
|
||||
|
||||
static void
|
||||
impl_ConfigArchiver_Archive__set_currentLocation (PortableServer_Servant servant,
|
||||
ConfigArchiver_Location location_ref,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
Archive *archive = ARCHIVE_FROM_SERVANT (servant);
|
||||
Location *location;
|
||||
|
||||
location = LOCATION (bonobo_object_from_servant (location_ref->servant));
|
||||
|
||||
if (location == NULL)
|
||||
/* bonobo_exception_set (ev, ex_ConfigArchiver_Archive_LocationNotFound) */;
|
||||
else
|
||||
archive_set_current_location (archive, location);
|
||||
}
|
||||
|
||||
static void
|
||||
impl_ConfigArchiver_Archive__set_currentLocationId (PortableServer_Servant servant,
|
||||
const CORBA_char *locid,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
archive_set_current_location_id (ARCHIVE_FROM_SERVANT (servant), locid);
|
||||
}
|
||||
|
||||
CORBA_char *
|
||||
impl_ConfigArchiver_Archive__get_currentLocationId (PortableServer_Servant servant,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
return CORBA_string_dup (archive_get_current_location_id (ARCHIVE_FROM_SERVANT (servant)));
|
||||
}
|
||||
|
||||
BONOBO_X_TYPE_FUNC_FULL (Archive, ConfigArchiver_Archive, BONOBO_X_OBJECT_TYPE, archive);
|
||||
|
||||
static void
|
||||
archive_init (Archive *archive)
|
||||
{
|
||||
|
@ -126,7 +221,20 @@ archive_class_init (ArchiveClass *klass)
|
|||
GTK_ARG_READWRITE | GTK_ARG_CONSTRUCT_ONLY,
|
||||
ARG_IS_GLOBAL);
|
||||
|
||||
parent_class = gtk_type_class (gtk_object_get_type ());
|
||||
klass->epv.getLocation = impl_ConfigArchiver_Archive_getLocation;
|
||||
klass->epv.createLocation = impl_ConfigArchiver_Archive_createLocation;
|
||||
klass->epv.getChildLocations = impl_ConfigArchiver_Archive_getChildLocations;
|
||||
|
||||
klass->epv._get_prefix = impl_ConfigArchiver_Archive__get_prefix;
|
||||
klass->epv._get_isGlobal = impl_ConfigArchiver_Archive__get_isGlobal;
|
||||
klass->epv._get_backendList = impl_ConfigArchiver_Archive__get_backendList;
|
||||
klass->epv._get_currentLocation = impl_ConfigArchiver_Archive__get_currentLocation;
|
||||
klass->epv._get_currentLocationId = impl_ConfigArchiver_Archive__get_currentLocationId;
|
||||
|
||||
klass->epv._set_currentLocation = impl_ConfigArchiver_Archive__set_currentLocation;
|
||||
klass->epv._set_currentLocationId = impl_ConfigArchiver_Archive__set_currentLocationId;
|
||||
|
||||
parent_class = gtk_type_class (BONOBO_X_OBJECT_TYPE);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -225,27 +333,22 @@ archive_construct (Archive *archive, gboolean is_new)
|
|||
* Return value: Reference to archive
|
||||
**/
|
||||
|
||||
GtkObject *
|
||||
BonoboObject *
|
||||
archive_load (gboolean is_global)
|
||||
{
|
||||
GtkObject *object;
|
||||
BonoboObject *object;
|
||||
gchar *prefix;
|
||||
|
||||
if (is_global && global_archive != NULL)
|
||||
return GTK_OBJECT (global_archive);
|
||||
else if (user_archive != NULL)
|
||||
return GTK_OBJECT (user_archive);
|
||||
|
||||
if (is_global)
|
||||
prefix = "/var/ximian-setup-tools";
|
||||
else
|
||||
prefix = g_concat_dir_and_file (g_get_home_dir (),
|
||||
".gnome/capplet-archive");
|
||||
|
||||
object = gtk_object_new (archive_get_type (),
|
||||
"prefix", prefix,
|
||||
"is-global", is_global,
|
||||
NULL);
|
||||
object = BONOBO_OBJECT (gtk_object_new (archive_get_type (),
|
||||
"prefix", prefix,
|
||||
"is-global", is_global,
|
||||
NULL));
|
||||
|
||||
if (!is_global)
|
||||
g_free (prefix);
|
||||
|
@ -253,22 +356,17 @@ archive_load (gboolean is_global)
|
|||
if (archive_construct (ARCHIVE (object), FALSE) == FALSE &&
|
||||
archive_construct (ARCHIVE (object), TRUE) == FALSE)
|
||||
{
|
||||
gtk_object_destroy (object);
|
||||
bonobo_object_unref (object);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (is_global)
|
||||
global_archive = ARCHIVE (object);
|
||||
else
|
||||
user_archive = ARCHIVE (object);
|
||||
|
||||
return object;
|
||||
}
|
||||
|
||||
static gint
|
||||
free_location_cb (gchar *locid, Location *location)
|
||||
free_location_cb (gchar *locid, BonoboObject *location)
|
||||
{
|
||||
location_close (location);
|
||||
bonobo_object_unref (location);
|
||||
g_free (locid);
|
||||
|
||||
return FALSE;
|
||||
|
@ -296,36 +394,16 @@ archive_destroy (GtkObject *object)
|
|||
if (archive->current_location_id != NULL)
|
||||
g_free (archive->current_location_id);
|
||||
|
||||
GTK_OBJECT_CLASS (parent_class)->destroy (GTK_OBJECT (archive));
|
||||
if (archive->backend_list != NULL)
|
||||
bonobo_object_unref (BONOBO_OBJECT (archive->backend_list));
|
||||
|
||||
if (archive->is_global)
|
||||
global_archive = NULL;
|
||||
else
|
||||
user_archive = NULL;
|
||||
GTK_OBJECT_CLASS (parent_class)->destroy (GTK_OBJECT (archive));
|
||||
|
||||
DEBUG_MSG ("Exit");
|
||||
}
|
||||
|
||||
/**
|
||||
* archive_close:
|
||||
* @archive:
|
||||
*
|
||||
* Closes the given archive handle. Also closes all locations under this
|
||||
* archive.
|
||||
**/
|
||||
|
||||
void
|
||||
archive_close (Archive *archive)
|
||||
{
|
||||
g_return_if_fail (archive != NULL);
|
||||
g_return_if_fail (IS_ARCHIVE (archive));
|
||||
|
||||
gtk_object_destroy (GTK_OBJECT (archive));
|
||||
}
|
||||
|
||||
/**
|
||||
* archive_get_location:
|
||||
* @archive:
|
||||
* @locid:
|
||||
*
|
||||
* Get a reference to the location with the given name.
|
||||
|
@ -334,57 +412,67 @@ archive_close (Archive *archive)
|
|||
**/
|
||||
|
||||
Location *
|
||||
archive_get_location (Archive *archive, const gchar *locid)
|
||||
archive_get_location (Archive *archive,
|
||||
const gchar *locid)
|
||||
{
|
||||
GtkObject *loc_obj;
|
||||
Location *loc_obj;
|
||||
gchar *tmp;
|
||||
|
||||
g_return_val_if_fail (archive != NULL, NULL);
|
||||
g_return_val_if_fail (IS_ARCHIVE (archive), NULL);
|
||||
g_return_val_if_fail (locid != NULL, NULL);
|
||||
|
||||
DEBUG_MSG ("Enter: %s", locid);
|
||||
|
||||
/* Stupid borken glib... */
|
||||
tmp = g_strdup (locid);
|
||||
loc_obj = g_tree_lookup (archive->locations, tmp);
|
||||
g_free (tmp);
|
||||
|
||||
if (!loc_obj) {
|
||||
loc_obj = location_open (archive, locid);
|
||||
if (loc_obj == NULL) {
|
||||
loc_obj = LOCATION (location_open (archive, locid));
|
||||
|
||||
if (!loc_obj) return NULL;
|
||||
|
||||
if (loc_obj)
|
||||
if (loc_obj == NULL)
|
||||
return NULL;
|
||||
else
|
||||
g_tree_insert (archive->locations,
|
||||
g_strdup (locid), loc_obj);
|
||||
} else {
|
||||
bonobo_object_ref (BONOBO_OBJECT (loc_obj));
|
||||
}
|
||||
|
||||
if (loc_obj) {
|
||||
gtk_object_ref (loc_obj);
|
||||
return LOCATION (loc_obj);
|
||||
} else {
|
||||
return NULL;
|
||||
}
|
||||
return loc_obj;
|
||||
}
|
||||
|
||||
/**
|
||||
* archive_register_location:
|
||||
* @archive:
|
||||
* @location:
|
||||
*
|
||||
* Register a location with the archive; invoked by location_new
|
||||
**/
|
||||
* archive_create_location:
|
||||
* @archive:
|
||||
* @location:
|
||||
*
|
||||
* Creates a new location
|
||||
*/
|
||||
|
||||
void
|
||||
archive_register_location (Archive *archive, Location *location)
|
||||
Location *
|
||||
archive_create_location (Archive *archive,
|
||||
const gchar *locid,
|
||||
const gchar *label,
|
||||
Location *parent)
|
||||
{
|
||||
g_return_if_fail (archive != NULL);
|
||||
g_return_if_fail (IS_ARCHIVE (archive));
|
||||
g_return_if_fail (location != NULL);
|
||||
g_return_if_fail (IS_LOCATION (location));
|
||||
Location *location;
|
||||
|
||||
g_tree_insert (archive->locations,
|
||||
g_strdup (location_get_id (location)),
|
||||
location);
|
||||
g_return_val_if_fail (archive != NULL, NULL);
|
||||
g_return_val_if_fail (IS_ARCHIVE (archive), NULL);
|
||||
g_return_val_if_fail (locid != NULL, NULL);
|
||||
g_return_val_if_fail (label != NULL, NULL);
|
||||
g_return_val_if_fail (parent == NULL || IS_LOCATION (parent), NULL);
|
||||
|
||||
location = LOCATION (location_new (archive, locid, label, parent));
|
||||
|
||||
if (location == NULL)
|
||||
return NULL;
|
||||
|
||||
g_tree_insert (archive->locations, g_strdup (locid), location);
|
||||
return location;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -406,7 +494,7 @@ archive_unregister_location (Archive *archive, Location *location)
|
|||
g_return_if_fail (IS_LOCATION (location));
|
||||
|
||||
if (GTK_OBJECT_DESTROYED (archive)) return;
|
||||
|
||||
|
||||
tmp = g_strdup (location_get_id (location));
|
||||
g_tree_remove (archive->locations, tmp);
|
||||
g_free (tmp);
|
||||
|
@ -414,7 +502,6 @@ archive_unregister_location (Archive *archive, Location *location)
|
|||
|
||||
/**
|
||||
* archive_get_current_location:
|
||||
* @archive: object
|
||||
*
|
||||
* Convenience function to get a pointer to the current location
|
||||
*
|
||||
|
@ -425,11 +512,13 @@ archive_unregister_location (Archive *archive, Location *location)
|
|||
Location *
|
||||
archive_get_current_location (Archive *archive)
|
||||
{
|
||||
const gchar *locid = archive_get_current_location_id (archive);
|
||||
const gchar *locid;
|
||||
|
||||
g_return_val_if_fail (archive != NULL, NULL);
|
||||
g_return_val_if_fail (IS_ARCHIVE (archive), NULL);
|
||||
|
||||
locid = archive_get_current_location_id (archive);
|
||||
|
||||
if (locid == NULL)
|
||||
return NULL;
|
||||
else
|
||||
|
@ -438,7 +527,6 @@ archive_get_current_location (Archive *archive)
|
|||
|
||||
/**
|
||||
* archive_set_current_location:
|
||||
* @archive: object
|
||||
* @location: Location to which to set archive
|
||||
*
|
||||
* Set the current location in an archive to the location given; apply
|
||||
|
@ -446,33 +534,35 @@ archive_get_current_location (Archive *archive)
|
|||
**/
|
||||
|
||||
void
|
||||
archive_set_current_location (Archive *archive, Location *location)
|
||||
archive_set_current_location (Archive *archive,
|
||||
Location *location)
|
||||
{
|
||||
Location *old_location;
|
||||
GList *backends;
|
||||
Location *old_location = archive_get_current_location (archive);
|
||||
|
||||
g_return_if_fail (archive != NULL);
|
||||
g_return_if_fail (IS_ARCHIVE (archive));
|
||||
g_return_if_fail (location != NULL);
|
||||
g_return_if_fail (IS_LOCATION (location));
|
||||
|
||||
old_location = archive_get_current_location (archive);
|
||||
|
||||
archive_set_current_location_id (archive, location_get_id (location));
|
||||
|
||||
backends = location_get_changed_backends (location, old_location);
|
||||
location_rollback_backends_to (location, NULL, backends, TRUE);
|
||||
g_list_free (backends);
|
||||
location_rollback_backends_to (location, NULL, 0, backends, TRUE);
|
||||
}
|
||||
|
||||
/**
|
||||
* archive_set_current_location_id:
|
||||
* @archive:
|
||||
* @name:
|
||||
*
|
||||
* Sets the current location's name, but does not invoke any rollback
|
||||
**/
|
||||
|
||||
void
|
||||
archive_set_current_location_id (Archive *archive, const gchar *locid)
|
||||
archive_set_current_location_id (Archive *archive,
|
||||
const gchar *locid)
|
||||
{
|
||||
g_return_if_fail (archive != NULL);
|
||||
g_return_if_fail (IS_ARCHIVE (archive));
|
||||
|
@ -497,7 +587,6 @@ archive_set_current_location_id (Archive *archive, const gchar *locid)
|
|||
|
||||
/**
|
||||
* archive_get_current_location_id:
|
||||
* @archive: object
|
||||
*
|
||||
* Get the name of the current location
|
||||
*
|
||||
|
@ -511,6 +600,7 @@ archive_get_current_location_id (Archive *archive)
|
|||
{
|
||||
gboolean def;
|
||||
Location *loc;
|
||||
Location *current_location;
|
||||
|
||||
g_return_val_if_fail (archive != NULL, NULL);
|
||||
g_return_val_if_fail (IS_ARCHIVE (archive), NULL);
|
||||
|
@ -526,18 +616,24 @@ archive_get_current_location_id (Archive *archive)
|
|||
("/capplet-archive/config/current/location=default", &def);
|
||||
|
||||
/* Create default location if it does not exist */
|
||||
if (def && archive_get_location
|
||||
(archive, archive->current_location_id) == NULL)
|
||||
{
|
||||
loc = LOCATION
|
||||
(location_new (archive,
|
||||
archive->current_location_id,
|
||||
NULL));
|
||||
if (archive->is_global &&
|
||||
location_store_full_snapshot (loc) < 0)
|
||||
{
|
||||
location_delete (loc);
|
||||
return NULL;
|
||||
if (def) {
|
||||
current_location =
|
||||
archive_get_location (archive, archive->current_location_id);
|
||||
|
||||
if (current_location == NULL) {
|
||||
loc = LOCATION
|
||||
(location_new (archive,
|
||||
archive->current_location_id,
|
||||
_("Default location"),
|
||||
NULL));
|
||||
if (archive->is_global &&
|
||||
location_store_full_snapshot (loc) < 0)
|
||||
{
|
||||
location_delete (loc);
|
||||
return NULL;
|
||||
}
|
||||
} else {
|
||||
bonobo_object_unref (BONOBO_OBJECT (current_location));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -603,10 +699,11 @@ static gint
|
|||
foreach_cb (gchar *key, Location *value, foreach_t *data)
|
||||
{
|
||||
if (location_get_parent (value) == data->parent)
|
||||
return data->callback (data->archive, value,
|
||||
data->user_data);
|
||||
else
|
||||
return 0;
|
||||
data->callback (data->archive, value, data->user_data);
|
||||
|
||||
bonobo_object_unref (BONOBO_OBJECT (value));
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -26,6 +26,8 @@
|
|||
|
||||
#include <gnome.h>
|
||||
|
||||
#include "ConfigArchiver.h"
|
||||
|
||||
#include "location.h"
|
||||
#include "backend-list.h"
|
||||
|
||||
|
@ -34,58 +36,62 @@
|
|||
#define IS_ARCHIVE(obj) GTK_CHECK_TYPE (obj, archive_get_type ())
|
||||
|
||||
typedef struct _ArchiveClass ArchiveClass;
|
||||
typedef gint (*LocationCB) (Archive *, Location *, gpointer);
|
||||
typedef void (*LocationCB) (Archive *, Location *, gpointer);
|
||||
|
||||
struct _Archive
|
||||
struct _Archive
|
||||
{
|
||||
GtkObject object;
|
||||
BonoboXObject object;
|
||||
|
||||
gchar *prefix;
|
||||
GTree *locations;
|
||||
gboolean is_global;
|
||||
gchar *prefix;
|
||||
GTree *locations;
|
||||
gboolean is_global;
|
||||
|
||||
gchar *current_location_id;
|
||||
gchar *current_location_id;
|
||||
|
||||
BackendList *backend_list;
|
||||
BackendList *backend_list;
|
||||
};
|
||||
|
||||
struct _ArchiveClass
|
||||
{
|
||||
GtkObjectClass parent;
|
||||
BonoboXObjectClass parent;
|
||||
|
||||
POA_ConfigArchiver_Archive__epv epv;
|
||||
};
|
||||
|
||||
guint archive_get_type (void);
|
||||
guint archive_get_type (void);
|
||||
|
||||
gboolean archive_construct (Archive *archive,
|
||||
gboolean is_new);
|
||||
gboolean archive_construct (Archive *archive,
|
||||
gboolean is_new);
|
||||
|
||||
GtkObject *archive_load (gboolean is_global);
|
||||
BonoboObject *archive_load (gboolean is_global);
|
||||
|
||||
void archive_close (Archive *archive);
|
||||
void archive_close (Archive *archive);
|
||||
|
||||
Location *archive_get_location (Archive *archive,
|
||||
const gchar *location);
|
||||
void archive_register_location (Archive *archive,
|
||||
Location *location);
|
||||
void archive_unregister_location (Archive *archive,
|
||||
Location *location);
|
||||
Location *archive_get_location (Archive *archive,
|
||||
const gchar *locid);
|
||||
Location *archive_create_location (Archive *archive,
|
||||
const gchar *locid,
|
||||
const gchar *label,
|
||||
Location *parent);
|
||||
void archive_unregister_location (Archive *archive,
|
||||
Location *location);
|
||||
|
||||
Location *archive_get_current_location (Archive *archive);
|
||||
void archive_set_current_location (Archive *archive,
|
||||
Location *location);
|
||||
Location *archive_get_current_location (Archive *archive);
|
||||
void archive_set_current_location (Archive *archive,
|
||||
Location *location);
|
||||
|
||||
const gchar *archive_get_current_location_id (Archive *archive);
|
||||
void archive_set_current_location_id (Archive *archive,
|
||||
const gchar *locid);
|
||||
const gchar *archive_get_current_location_id (Archive *archive);
|
||||
void archive_set_current_location_id (Archive *archive,
|
||||
const gchar *locid);
|
||||
|
||||
const gchar *archive_get_prefix (Archive *archive);
|
||||
gboolean archive_is_global (Archive *archive);
|
||||
const gchar *archive_get_prefix (Archive *archive);
|
||||
gboolean archive_is_global (Archive *archive);
|
||||
|
||||
BackendList *archive_get_backend_list (Archive *archive);
|
||||
BackendList *archive_get_backend_list (Archive *archive);
|
||||
|
||||
void archive_foreach_child_location (Archive *archive,
|
||||
LocationCB callback,
|
||||
Location *parent,
|
||||
gpointer data);
|
||||
void archive_foreach_child_location (Archive *archive,
|
||||
LocationCB callback,
|
||||
Location *parent,
|
||||
gpointer data);
|
||||
|
||||
#endif /* __ARCHIVE */
|
||||
|
|
422
archiver/archiver-client.c
Normal file
422
archiver/archiver-client.c
Normal file
|
@ -0,0 +1,422 @@
|
|||
/* -*- mode: c; style: linux -*- */
|
||||
|
||||
/* archiver-client.c
|
||||
* Copyright (C) 2000-2001 Ximian, Inc.
|
||||
*
|
||||
* Written by Bradford Hovinen (hovinen@ximian.com)
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2, 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 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.
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include <bonobo.h>
|
||||
#include <gnome-xml/parser.h>
|
||||
|
||||
#include "archiver-client.h"
|
||||
|
||||
static void merge_xml_docs (xmlDocPtr child_doc,
|
||||
xmlDocPtr parent_doc);
|
||||
static void subtract_xml_doc (xmlDocPtr child_doc,
|
||||
xmlDocPtr parent_doc,
|
||||
gboolean strict);
|
||||
static void merge_xml_nodes (xmlNodePtr node1,
|
||||
xmlNodePtr node2);
|
||||
static xmlNodePtr subtract_xml_node (xmlNodePtr node1,
|
||||
xmlNodePtr node2,
|
||||
gboolean strict);
|
||||
static gboolean compare_xml_nodes (xmlNodePtr node1, xmlNodePtr node2);
|
||||
|
||||
/**
|
||||
* location_load_rollback_data
|
||||
* @location:
|
||||
* @date:
|
||||
* @steps:
|
||||
* @backend_id:
|
||||
* @parent_chain:
|
||||
*
|
||||
* Loads the XML data for rolling back as specified and returns the document
|
||||
* object
|
||||
**/
|
||||
|
||||
xmlDocPtr
|
||||
location_client_load_rollback_data (ConfigArchiver_Location location,
|
||||
struct tm *date,
|
||||
guint steps,
|
||||
gchar *backend_id,
|
||||
gboolean parent_chain,
|
||||
CORBA_Environment *opt_ev)
|
||||
{
|
||||
gchar *filename;
|
||||
time_t time_g;
|
||||
xmlDocPtr doc = NULL, parent_doc = NULL;
|
||||
ConfigArchiver_ContainmentType type = ConfigArchiver_CONTAIN_FULL;
|
||||
ConfigArchiver_Location parent = CORBA_OBJECT_NIL;
|
||||
CORBA_Environment my_ev;
|
||||
|
||||
|
||||
g_return_val_if_fail (location != CORBA_OBJECT_NIL, NULL);
|
||||
|
||||
if (opt_ev == NULL) {
|
||||
opt_ev = &my_ev;
|
||||
CORBA_exception_init (opt_ev);
|
||||
}
|
||||
|
||||
if (date != NULL)
|
||||
time_g = mktime (date);
|
||||
else
|
||||
time_g = 0;
|
||||
|
||||
filename = ConfigArchiver_Location_getRollbackFilename
|
||||
(location, time_g, steps, backend_id, parent_chain, opt_ev);
|
||||
|
||||
if (filename != NULL)
|
||||
doc = xmlParseFile (filename);
|
||||
else if (parent_chain)
|
||||
type = ConfigArchiver_Location_contains (location, backend_id, opt_ev);
|
||||
|
||||
if (type == ConfigArchiver_CONTAIN_PARTIAL)
|
||||
parent = ConfigArchiver_Location__get_parent (location, opt_ev);
|
||||
|
||||
if (parent != CORBA_OBJECT_NIL) {
|
||||
parent_doc = location_client_load_rollback_data
|
||||
(parent, date, steps, backend_id, TRUE, opt_ev);
|
||||
bonobo_object_release_unref (parent, NULL);
|
||||
}
|
||||
|
||||
if (doc != NULL && parent_doc != NULL)
|
||||
merge_xml_docs (doc, parent_doc);
|
||||
else if (parent_doc != NULL)
|
||||
doc = parent_doc;
|
||||
|
||||
if (opt_ev == &my_ev)
|
||||
CORBA_exception_free (opt_ev);
|
||||
|
||||
return doc;
|
||||
}
|
||||
|
||||
/**
|
||||
* location_client_store_xml:
|
||||
* @location:
|
||||
* @backend_id:
|
||||
* @input:
|
||||
* @store_type: STORE_FULL means blindly store the data, without
|
||||
* modification. STORE_COMPARE_PARENT means subtract the settings the parent
|
||||
* has that are different and store the result. STORE_MASK_PREVIOUS means
|
||||
* store only those settings that are reflected in the previous logged data;
|
||||
* if there do not exist such data, act as in STORE_COMPARE_PARENT
|
||||
* @opt_ev:
|
||||
*
|
||||
* Store configuration data from the given XML document object in the location
|
||||
* under the given backend id
|
||||
**/
|
||||
|
||||
void
|
||||
location_client_store_xml (ConfigArchiver_Location location,
|
||||
gchar *backend_id,
|
||||
xmlDocPtr xml_doc,
|
||||
ConfigArchiver_StoreType store_type,
|
||||
CORBA_Environment *opt_ev)
|
||||
{
|
||||
xmlDocPtr parent_doc, prev_doc = NULL;
|
||||
char *filename;
|
||||
ConfigArchiver_ContainmentType contain_type;
|
||||
ConfigArchiver_Location parent;
|
||||
CORBA_Environment my_ev;
|
||||
|
||||
g_return_if_fail (location != CORBA_OBJECT_NIL);
|
||||
g_return_if_fail (xml_doc != NULL);
|
||||
|
||||
if (opt_ev == NULL) {
|
||||
opt_ev = &my_ev;
|
||||
CORBA_exception_init (opt_ev);
|
||||
}
|
||||
|
||||
contain_type = ConfigArchiver_Location_contains (location, backend_id, opt_ev);
|
||||
parent = ConfigArchiver_Location__get_parent (location, opt_ev);
|
||||
|
||||
if (contain_type == ConfigArchiver_CONTAIN_NONE) {
|
||||
if (parent == CORBA_OBJECT_NIL) {
|
||||
fprintf (stderr, "Could not find a location in the " \
|
||||
"tree ancestry that stores this " \
|
||||
"backend: %s.\n", backend_id);
|
||||
} else {
|
||||
location_client_store_xml (parent, backend_id, xml_doc, store_type, opt_ev);
|
||||
bonobo_object_release_unref (parent, NULL);
|
||||
}
|
||||
|
||||
if (opt_ev == &my_ev)
|
||||
CORBA_exception_free (opt_ev);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (contain_type == ConfigArchiver_CONTAIN_PARTIAL && store_type != ConfigArchiver_STORE_FULL && parent != CORBA_OBJECT_NIL) {
|
||||
g_assert (store_type == ConfigArchiver_STORE_MASK_PREVIOUS ||
|
||||
store_type == ConfigArchiver_STORE_COMPARE_PARENT);
|
||||
|
||||
parent_doc = location_client_load_rollback_data
|
||||
(parent, NULL, 0, backend_id, TRUE, opt_ev);
|
||||
|
||||
if (store_type == ConfigArchiver_STORE_MASK_PREVIOUS)
|
||||
prev_doc = location_client_load_rollback_data (location, NULL, 0, backend_id, FALSE, opt_ev);
|
||||
|
||||
if (store_type == ConfigArchiver_STORE_COMPARE_PARENT) {
|
||||
subtract_xml_doc (xml_doc, parent_doc, FALSE);
|
||||
} else {
|
||||
subtract_xml_doc (parent_doc, prev_doc, FALSE);
|
||||
subtract_xml_doc (xml_doc, parent_doc, TRUE);
|
||||
}
|
||||
|
||||
xmlFreeDoc (parent_doc);
|
||||
|
||||
if (prev_doc != NULL)
|
||||
xmlFreeDoc (prev_doc);
|
||||
}
|
||||
|
||||
if (parent != CORBA_OBJECT_NIL)
|
||||
bonobo_object_release_unref (parent, NULL);
|
||||
|
||||
filename = ConfigArchiver_Location_getStorageFilename (location, backend_id, store_type == ConfigArchiver_STORE_DEFAULT, opt_ev);
|
||||
xmlSaveFile (filename, xml_doc);
|
||||
CORBA_free (filename);
|
||||
|
||||
if (opt_ev == &my_ev)
|
||||
CORBA_exception_free (opt_ev);
|
||||
}
|
||||
|
||||
static void
|
||||
merge_xml_docs (xmlDocPtr child_doc, xmlDocPtr parent_doc)
|
||||
{
|
||||
merge_xml_nodes (xmlDocGetRootElement (child_doc),
|
||||
xmlDocGetRootElement (parent_doc));
|
||||
}
|
||||
|
||||
static void
|
||||
subtract_xml_doc (xmlDocPtr child_doc, xmlDocPtr parent_doc, gboolean strict)
|
||||
{
|
||||
subtract_xml_node (xmlDocGetRootElement (child_doc),
|
||||
xmlDocGetRootElement (parent_doc), strict);
|
||||
}
|
||||
|
||||
/* Merge contents of node1 and node2, where node1 overrides node2 as
|
||||
* appropriate
|
||||
*
|
||||
* Notes: Two XML nodes are considered to be "the same" iff their names and
|
||||
* all names and values of their attributes are the same. If that is not the
|
||||
* case, they are considered "different" and will both be present in the
|
||||
* merged node. If nodes are "the same", then this algorithm is called
|
||||
* recursively. If nodes are CDATA, then node1 overrides node2 and the
|
||||
* resulting node is just node1. The node merging is order-independent; child
|
||||
* node from one tree are compared with all child nodes of the other tree
|
||||
* regardless of the order they appear in. Hence one may have documents with
|
||||
* different node orderings and the algorithm should still run correctly. It
|
||||
* will not, however, run correctly in cases when the agent using this
|
||||
* facility depends on the nodes being in a particular order.
|
||||
*
|
||||
* This XML node merging/comparison facility requires that the following
|
||||
* standard be set for DTDs:
|
||||
*
|
||||
* Attributes' sole purpose is to identify a node. For example, a network
|
||||
* configuration DTD might have an element like <interface name="eth0"> with a
|
||||
* bunch of child nodes to configure that interface. The attribute "name" does
|
||||
* not specify the configuration for the interface. It differentiates the node
|
||||
* from the configuration for, say, interface eth1. Conversely, a node must be
|
||||
* completely identified by its attributes. One cannot include identification
|
||||
* information in the node's children, since otherwise the merging and
|
||||
* subtraction algorithms will not know what to look for.
|
||||
*
|
||||
* As a corollary to the above, all configuration information must ultimately
|
||||
* be in text nodes. For example, a text string might be stored as
|
||||
* <configuration-item>my-value</configuration-item> but never as
|
||||
* <configuration-item value="my-value"/>. As an example, if the latter is
|
||||
* used, a child location might override a parent's setting for
|
||||
* configuration-item. This algorithm will interpret those as different nodes
|
||||
* and include them both in the merged result, since it will not have any way
|
||||
* of knowing that they are really the same node with different
|
||||
* configuration.
|
||||
*/
|
||||
|
||||
static void
|
||||
merge_xml_nodes (xmlNodePtr node1, xmlNodePtr node2)
|
||||
{
|
||||
xmlNodePtr child, tmp, iref;
|
||||
GList *node1_children = NULL, *i;
|
||||
gboolean found;
|
||||
|
||||
if (node1->type == XML_TEXT_NODE)
|
||||
return;
|
||||
|
||||
for (child = node1->childs; child != NULL; child = child->next)
|
||||
node1_children = g_list_prepend (node1_children, child);
|
||||
|
||||
node1_children = g_list_reverse (node1_children);
|
||||
|
||||
child = node2->childs;
|
||||
|
||||
while (child != NULL) {
|
||||
tmp = child->next;
|
||||
|
||||
i = node1_children; found = FALSE;
|
||||
|
||||
while (i != NULL) {
|
||||
iref = (xmlNodePtr) i->data;
|
||||
|
||||
if (compare_xml_nodes (iref, child)) {
|
||||
merge_xml_nodes (iref, child);
|
||||
if (i == node1_children)
|
||||
node1_children = node1_children->next;
|
||||
g_list_remove_link (node1_children, i);
|
||||
g_list_free_1 (i);
|
||||
found = TRUE;
|
||||
break;
|
||||
} else {
|
||||
i = i->next;
|
||||
}
|
||||
}
|
||||
|
||||
if (found == FALSE) {
|
||||
xmlUnlinkNode (child);
|
||||
xmlAddChild (node1, child);
|
||||
}
|
||||
|
||||
child = tmp;
|
||||
}
|
||||
|
||||
g_list_free (node1_children);
|
||||
}
|
||||
|
||||
/* Modifies node1 so that it only contains the parts different from node2;
|
||||
* returns the modified node or NULL if the node should be destroyed
|
||||
*
|
||||
* strict determines whether the settings themselves are compared; it should
|
||||
* be set to FALSE when the trees are being compared for the purpose of
|
||||
* seeing what settings should be included in a tree and TRUE when one wants
|
||||
* to restrict the settings included in a tree to those that have already been
|
||||
* specified
|
||||
*/
|
||||
|
||||
static xmlNodePtr
|
||||
subtract_xml_node (xmlNodePtr node1, xmlNodePtr node2, gboolean strict)
|
||||
{
|
||||
xmlNodePtr child, tmp, iref;
|
||||
GList *node2_children = NULL, *i;
|
||||
gboolean found, same, all_same = TRUE;
|
||||
|
||||
if (node1->type == XML_TEXT_NODE) {
|
||||
if (node2->type == XML_TEXT_NODE &&
|
||||
(strict || !strcmp (xmlNodeGetContent (node1),
|
||||
xmlNodeGetContent (node2))))
|
||||
return NULL;
|
||||
else
|
||||
return node1;
|
||||
}
|
||||
|
||||
if (node1->childs == NULL && node2->childs == NULL)
|
||||
return NULL;
|
||||
|
||||
for (child = node2->childs; child != NULL; child = child->next)
|
||||
node2_children = g_list_prepend (node2_children, child);
|
||||
|
||||
node2_children = g_list_reverse (node2_children);
|
||||
|
||||
child = node1->childs;
|
||||
|
||||
while (child != NULL) {
|
||||
tmp = child->next;
|
||||
i = node2_children; found = FALSE; all_same = TRUE;
|
||||
|
||||
while (i != NULL) {
|
||||
iref = (xmlNodePtr) i->data;
|
||||
|
||||
if (compare_xml_nodes (child, iref)) {
|
||||
same = (subtract_xml_node
|
||||
(child, iref, strict) == NULL);
|
||||
all_same = all_same && same;
|
||||
|
||||
if (same) {
|
||||
xmlUnlinkNode (child);
|
||||
xmlFreeNode (child);
|
||||
}
|
||||
|
||||
if (i == node2_children)
|
||||
node2_children = node2_children->next;
|
||||
g_list_remove_link (node2_children, i);
|
||||
g_list_free_1 (i);
|
||||
found = TRUE;
|
||||
break;
|
||||
} else {
|
||||
i = i->next;
|
||||
}
|
||||
}
|
||||
|
||||
if (!found)
|
||||
all_same = FALSE;
|
||||
|
||||
child = tmp;
|
||||
}
|
||||
|
||||
g_list_free (node2_children);
|
||||
|
||||
if (all_same)
|
||||
return NULL;
|
||||
else
|
||||
return node1;
|
||||
}
|
||||
|
||||
/* Return TRUE iff node1 and node2 are "the same" in the sense defined above */
|
||||
|
||||
static gboolean
|
||||
compare_xml_nodes (xmlNodePtr node1, xmlNodePtr node2)
|
||||
{
|
||||
xmlAttrPtr attr;
|
||||
gint count = 0;
|
||||
|
||||
if (strcmp (node1->name, node2->name))
|
||||
return FALSE;
|
||||
|
||||
/* FIXME: This is worst case O(n^2), which can add up. Could we
|
||||
* optimize for the case where people have attributes in the same
|
||||
* order, or does not not matter? It probably does not matter, though,
|
||||
* since people don't generally have more than one or two attributes
|
||||
* in a tag anyway.
|
||||
*/
|
||||
|
||||
for (attr = node1->properties; attr != NULL; attr = attr->next) {
|
||||
g_assert (xmlNodeIsText (attr->val));
|
||||
|
||||
if (strcmp (xmlNodeGetContent (attr->val),
|
||||
xmlGetProp (node2, attr->name)))
|
||||
return FALSE;
|
||||
|
||||
count++;
|
||||
}
|
||||
|
||||
/* FIXME: Is checking if the two nodes have the same number of
|
||||
* attributes the correct policy here? Should we instead merge the
|
||||
* attribute(s) that node1 is missing?
|
||||
*/
|
||||
|
||||
for (attr = node2->properties; attr != NULL; attr = attr->next)
|
||||
count--;
|
||||
|
||||
if (count == 0)
|
||||
return TRUE;
|
||||
else
|
||||
return FALSE;
|
||||
}
|
46
archiver/archiver-client.h
Normal file
46
archiver/archiver-client.h
Normal file
|
@ -0,0 +1,46 @@
|
|||
/* -*- mode: c; style: linux -*- */
|
||||
|
||||
/* archiver-client.h
|
||||
* Copyright (C) 2001 Ximian, Inc.
|
||||
*
|
||||
* Written by Bradford Hovinen (hovinen@ximian.com)
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2, 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 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.
|
||||
*/
|
||||
|
||||
#ifndef __ARCHIVER_CLIENT_H
|
||||
#define __ARCHIVER_CLIENT_H
|
||||
|
||||
#include <gnome.h>
|
||||
#include <libxml/tree.h>
|
||||
#include <time.h>
|
||||
|
||||
#include "ConfigArchiver.h"
|
||||
|
||||
xmlDocPtr location_client_load_rollback_data (ConfigArchiver_Location location,
|
||||
struct tm *date,
|
||||
guint steps,
|
||||
gchar *backend_id,
|
||||
gboolean parent_chain,
|
||||
CORBA_Environment *opt_ev);
|
||||
|
||||
void location_client_store_xml (ConfigArchiver_Location location,
|
||||
gchar *backend_id,
|
||||
xmlDocPtr xml_doc,
|
||||
ConfigArchiver_StoreType store_type,
|
||||
CORBA_Environment *opt_ev);
|
||||
|
||||
#endif /* __ARCHIVER_CLIENT_H */
|
|
@ -42,7 +42,9 @@ struct _BackendListPrivate
|
|||
GList *backend_ids;
|
||||
};
|
||||
|
||||
static GtkObjectClass *parent_class;
|
||||
#define BACKEND_LIST_FROM_SERVANT(servant) (BACKEND_LIST (bonobo_object_from_servant (servant)))
|
||||
|
||||
static BonoboXObjectClass *parent_class;
|
||||
|
||||
static void backend_list_init (BackendList *backend_list);
|
||||
static void backend_list_class_init (BackendListClass *class);
|
||||
|
@ -59,30 +61,64 @@ static void backend_list_finalize (GtkObject *object);
|
|||
static void do_load (BackendList *backend_list);
|
||||
static void do_save (BackendList *backend_list);
|
||||
|
||||
guint
|
||||
backend_list_get_type (void)
|
||||
/* CORBA interface methods */
|
||||
|
||||
static CORBA_boolean
|
||||
impl_ConfigArchiver_BackendList_contains (PortableServer_Servant servant,
|
||||
const CORBA_char *backend_id,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
static guint backend_list_type = 0;
|
||||
|
||||
if (!backend_list_type) {
|
||||
GtkTypeInfo backend_list_info = {
|
||||
"BackendList",
|
||||
sizeof (BackendList),
|
||||
sizeof (BackendListClass),
|
||||
(GtkClassInitFunc) backend_list_class_init,
|
||||
(GtkObjectInitFunc) backend_list_init,
|
||||
(GtkArgSetFunc) NULL,
|
||||
(GtkArgGetFunc) NULL
|
||||
};
|
||||
|
||||
backend_list_type =
|
||||
gtk_type_unique (gtk_object_get_type (),
|
||||
&backend_list_info);
|
||||
}
|
||||
|
||||
return backend_list_type;
|
||||
return backend_list_contains (BACKEND_LIST_FROM_SERVANT (servant), backend_id);
|
||||
}
|
||||
|
||||
static void
|
||||
impl_ConfigArchiver_BackendList_add (PortableServer_Servant servant,
|
||||
const CORBA_char *backend_id,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
backend_list_add (BACKEND_LIST_FROM_SERVANT (servant), backend_id);
|
||||
}
|
||||
|
||||
static void
|
||||
impl_ConfigArchiver_BackendList_remove (PortableServer_Servant servant,
|
||||
const CORBA_char *backend_id,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
backend_list_remove (BACKEND_LIST_FROM_SERVANT (servant), backend_id);
|
||||
}
|
||||
|
||||
static void
|
||||
impl_ConfigArchiver_BackendList_save (PortableServer_Servant servant,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
backend_list_save (BACKEND_LIST_FROM_SERVANT (servant));
|
||||
}
|
||||
|
||||
static ConfigArchiver_StringSeq *
|
||||
impl_ConfigArchiver_BackendList__get_backends (PortableServer_Servant servant,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
ConfigArchiver_StringSeq *seq;
|
||||
BackendList *backend_list = BACKEND_LIST_FROM_SERVANT (servant);
|
||||
guint i = 0;
|
||||
GList *node;
|
||||
|
||||
g_return_val_if_fail (backend_list != NULL, NULL);
|
||||
g_return_val_if_fail (IS_BACKEND_LIST (backend_list), NULL);
|
||||
|
||||
seq = ConfigArchiver_StringSeq__alloc ();
|
||||
seq->_length = g_list_length (backend_list->p->backend_ids);
|
||||
seq->_buffer = CORBA_sequence_CORBA_string_allocbuf (seq->_length);
|
||||
CORBA_sequence_set_release (seq, TRUE);
|
||||
|
||||
for (node = backend_list->p->backend_ids; node != NULL; node = node->next)
|
||||
seq->_buffer[i++] = CORBA_string_dup (node->data);
|
||||
|
||||
return seq;
|
||||
}
|
||||
|
||||
BONOBO_X_TYPE_FUNC_FULL (BackendList, ConfigArchiver_BackendList, BONOBO_X_OBJECT_TYPE, backend_list);
|
||||
|
||||
static void
|
||||
backend_list_init (BackendList *backend_list)
|
||||
{
|
||||
|
@ -104,8 +140,15 @@ backend_list_class_init (BackendListClass *class)
|
|||
object_class->set_arg = backend_list_set_arg;
|
||||
object_class->get_arg = backend_list_get_arg;
|
||||
|
||||
parent_class = GTK_OBJECT_CLASS
|
||||
(gtk_type_class (gtk_object_get_type ()));
|
||||
class->epv.contains = impl_ConfigArchiver_BackendList_contains;
|
||||
class->epv.add = impl_ConfigArchiver_BackendList_add;
|
||||
class->epv.remove = impl_ConfigArchiver_BackendList_remove;
|
||||
class->epv.save = impl_ConfigArchiver_BackendList_save;
|
||||
|
||||
class->epv._get_backends = impl_ConfigArchiver_BackendList__get_backends;
|
||||
|
||||
parent_class = BONOBO_X_OBJECT_CLASS
|
||||
(gtk_type_class (BONOBO_X_OBJECT_TYPE));
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -173,16 +216,17 @@ backend_list_finalize (GtkObject *object)
|
|||
GTK_OBJECT_CLASS (parent_class)->finalize (object);
|
||||
}
|
||||
|
||||
GtkObject *
|
||||
BonoboObject *
|
||||
backend_list_new (gboolean is_global)
|
||||
{
|
||||
return gtk_object_new (backend_list_get_type (),
|
||||
"is-global", is_global,
|
||||
NULL);
|
||||
return BONOBO_OBJECT
|
||||
(gtk_object_new (backend_list_get_type (),
|
||||
"is-global", is_global,
|
||||
NULL));
|
||||
}
|
||||
|
||||
gboolean
|
||||
backend_list_contains (BackendList *backend_list, gchar *backend_id)
|
||||
backend_list_contains (BackendList *backend_list, const gchar *backend_id)
|
||||
{
|
||||
GList *node;
|
||||
|
||||
|
@ -226,25 +270,33 @@ backend_list_foreach (BackendList *backend_list, BackendCB callback,
|
|||
}
|
||||
|
||||
void
|
||||
backend_list_add (BackendList *backend_list, gchar *backend_id)
|
||||
backend_list_add (BackendList *backend_list, const gchar *backend_id)
|
||||
{
|
||||
g_return_if_fail (backend_list != NULL);
|
||||
g_return_if_fail (IS_BACKEND_LIST (backend_list));
|
||||
g_return_if_fail (backend_id != NULL);
|
||||
|
||||
backend_list->p->backend_ids =
|
||||
g_list_prepend (backend_list->p->backend_ids, backend_id);
|
||||
g_list_prepend (backend_list->p->backend_ids, g_strdup (backend_id));
|
||||
}
|
||||
|
||||
void
|
||||
backend_list_remove (BackendList *backend_list, gchar *backend_id)
|
||||
backend_list_remove (BackendList *backend_list, const gchar *backend_id)
|
||||
{
|
||||
gchar *tmp;
|
||||
GList *node;
|
||||
|
||||
g_return_if_fail (backend_list != NULL);
|
||||
g_return_if_fail (IS_BACKEND_LIST (backend_list));
|
||||
g_return_if_fail (backend_id != NULL);
|
||||
|
||||
tmp = g_strdup (backend_id);
|
||||
node = g_list_find (backend_list->p->backend_ids, tmp);
|
||||
backend_list->p->backend_ids =
|
||||
g_list_remove (backend_list->p->backend_ids, backend_id);
|
||||
g_list_remove_link (backend_list->p->backend_ids, node);
|
||||
g_free (node->data);
|
||||
g_free (tmp);
|
||||
g_list_free_1 (node);
|
||||
}
|
||||
|
||||
void
|
||||
|
|
|
@ -25,6 +25,9 @@
|
|||
#define __BACKEND_LIST_H
|
||||
|
||||
#include <gnome.h>
|
||||
#include <bonobo.h>
|
||||
|
||||
#include "ConfigArchiver.h"
|
||||
|
||||
BEGIN_GNOME_DECLS
|
||||
|
||||
|
@ -40,33 +43,35 @@ typedef gint (*BackendCB) (BackendList *, gchar *, gpointer);
|
|||
|
||||
struct _BackendList
|
||||
{
|
||||
GtkObject parent;
|
||||
BonoboXObject parent;
|
||||
|
||||
BackendListPrivate *p;
|
||||
};
|
||||
|
||||
struct _BackendListClass
|
||||
{
|
||||
GtkObjectClass gtk_object_class;
|
||||
BonoboXObjectClass parent_class;
|
||||
|
||||
POA_ConfigArchiver_BackendList__epv epv;
|
||||
};
|
||||
|
||||
guint backend_list_get_type (void);
|
||||
guint backend_list_get_type (void);
|
||||
|
||||
GtkObject *backend_list_new (gboolean is_global);
|
||||
BonoboObject *backend_list_new (gboolean is_global);
|
||||
|
||||
gboolean backend_list_contains (BackendList *backend_list,
|
||||
gchar *backend_id);
|
||||
gboolean backend_list_contains (BackendList *backend_list,
|
||||
const gchar *backend_id);
|
||||
|
||||
gboolean backend_list_foreach (BackendList *backend_list,
|
||||
BackendCB callback,
|
||||
gpointer data);
|
||||
gboolean backend_list_foreach (BackendList *backend_list,
|
||||
BackendCB callback,
|
||||
gpointer data);
|
||||
|
||||
void backend_list_add (BackendList *backend_list,
|
||||
gchar *backend_id);
|
||||
void backend_list_remove (BackendList *backend_list,
|
||||
gchar *backend_id);
|
||||
void backend_list_add (BackendList *backend_list,
|
||||
const gchar *backend_id);
|
||||
void backend_list_remove (BackendList *backend_list,
|
||||
const gchar *backend_id);
|
||||
|
||||
void backend_list_save (BackendList *backend_list);
|
||||
void backend_list_save (BackendList *backend_list);
|
||||
|
||||
END_GNOME_DECLS
|
||||
|
||||
|
|
|
@ -223,8 +223,8 @@ real_sync (BonoboConfigDatabase *db,
|
|||
if (!db->writeable)
|
||||
return;
|
||||
|
||||
location_store_xml (archiver_db->location, archiver_db->backend_id,
|
||||
archiver_db->doc, STORE_MASK_PREVIOUS);
|
||||
location_client_store_xml (archiver_db->location, archiver_db->backend_id,
|
||||
archiver_db->doc, ConfigArchiver_STORE_MASK_PREVIOUS, ev);
|
||||
|
||||
arg = bonobo_arg_new (BONOBO_ARG_NULL);
|
||||
bonobo_event_source_notify_listeners (archiver_db->es, "Bonobo/ConfigDatabase:sync", arg, ev);
|
||||
|
@ -470,29 +470,12 @@ pb_get_fn (BonoboPropertyBag *bag, BonoboArg *arg,
|
|||
gpointer user_data)
|
||||
{
|
||||
BonoboConfigArchiver *archiver_db = BONOBO_CONFIG_ARCHIVER (user_data);
|
||||
gint id;
|
||||
ConfigLog *log;
|
||||
struct tm *mod;
|
||||
time_t val;
|
||||
extern int daylight;
|
||||
|
||||
log = location_get_config_log (archiver_db->location);
|
||||
id = config_log_get_rollback_id_by_steps (log, 0, archiver_db->real_name);
|
||||
if (id < 0)
|
||||
{
|
||||
BONOBO_ARG_SET_GENERAL (arg, 0,
|
||||
TC_ulonglong, CORBA_unsigned_long_long, NULL);
|
||||
return;
|
||||
}
|
||||
val = ConfigArchiver_Location_getModificationTime
|
||||
(archiver_db->location, archiver_db->backend_id, ev);
|
||||
|
||||
mod = config_log_get_date_for_id (log, id);
|
||||
val = mktime (mod);
|
||||
g_print ("%i\n", mod->tm_hour);
|
||||
if (daylight)
|
||||
val -= 3600;
|
||||
|
||||
BONOBO_ARG_SET_GENERAL (arg, val,
|
||||
TC_ulonglong, CORBA_unsigned_long_long, NULL);
|
||||
BONOBO_ARG_SET_GENERAL (arg, val, TC_ulonglong, CORBA_unsigned_long_long, NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -509,6 +492,8 @@ bonobo_config_archiver_destroy (GtkObject *object)
|
|||
BonoboConfigArchiver *archiver_db = BONOBO_CONFIG_ARCHIVER (object);
|
||||
CORBA_Environment ev;
|
||||
|
||||
DEBUG_MSG ("Enter");
|
||||
|
||||
CORBA_exception_init (&ev);
|
||||
|
||||
if (archiver_db->real_name != NULL) {
|
||||
|
@ -518,16 +503,24 @@ bonobo_config_archiver_destroy (GtkObject *object)
|
|||
|
||||
CORBA_exception_free (&ev);
|
||||
|
||||
if (archiver_db->doc)
|
||||
if (archiver_db->doc != NULL)
|
||||
xmlFreeDoc (archiver_db->doc);
|
||||
|
||||
if (archiver_db->filename)
|
||||
if (archiver_db->filename != NULL)
|
||||
g_free (archiver_db->filename);
|
||||
|
||||
if (archiver_db->fp)
|
||||
if (archiver_db->fp != NULL)
|
||||
fclose (archiver_db->fp);
|
||||
|
||||
if (archiver_db->location != CORBA_OBJECT_NIL)
|
||||
bonobo_object_release_unref (archiver_db->location, NULL);
|
||||
|
||||
if (archiver_db->archive != CORBA_OBJECT_NIL)
|
||||
bonobo_object_release_unref (archiver_db->archive, NULL);
|
||||
|
||||
parent_class->destroy (object);
|
||||
|
||||
DEBUG_MSG ("Exit");
|
||||
}
|
||||
|
||||
|
||||
|
@ -632,60 +625,67 @@ fill_cache (BonoboConfigArchiver *archiver_db)
|
|||
}
|
||||
|
||||
Bonobo_ConfigDatabase
|
||||
bonobo_config_archiver_new (const char *backend_id, const char *location_id)
|
||||
bonobo_config_archiver_new (Bonobo_Moniker parent,
|
||||
const Bonobo_ResolveOptions *options,
|
||||
const char *backend_id,
|
||||
const char *location_id,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
BonoboConfigArchiver *archiver_db;
|
||||
Bonobo_ConfigDatabase db;
|
||||
CORBA_Environment ev;
|
||||
gchar *real_name;
|
||||
|
||||
static Archive *archive = NULL;
|
||||
|
||||
g_return_val_if_fail (backend_id != NULL, NULL);
|
||||
|
||||
CORBA_exception_init (&ev);
|
||||
DEBUG_MSG ("Enter");
|
||||
|
||||
if (location_id == NULL)
|
||||
real_name = g_strdup (backend_id);
|
||||
else
|
||||
real_name = g_strconcat ("[", location_id, "]", backend_id, NULL);
|
||||
|
||||
db = bonobo_url_lookup ("BONOBO_CONF:ARCHIVER", real_name, &ev);
|
||||
db = bonobo_url_lookup ("BONOBO_CONF:ARCHIVER", real_name, ev);
|
||||
|
||||
if (BONOBO_EX (&ev))
|
||||
if (BONOBO_EX (ev)) {
|
||||
db = CORBA_OBJECT_NIL;
|
||||
|
||||
CORBA_exception_free (&ev);
|
||||
CORBA_exception_init (ev);
|
||||
}
|
||||
|
||||
if (db) {
|
||||
g_free (real_name);
|
||||
return bonobo_object_dup_ref (db, NULL);
|
||||
}
|
||||
|
||||
if (!(archiver_db = gtk_type_new (BONOBO_CONFIG_ARCHIVER_TYPE))) {
|
||||
DEBUG_MSG ("Creating object");
|
||||
|
||||
if ((archiver_db = gtk_type_new (BONOBO_CONFIG_ARCHIVER_TYPE)) == NULL) {
|
||||
g_free (real_name);
|
||||
return CORBA_OBJECT_NIL;
|
||||
}
|
||||
|
||||
if (archive == NULL)
|
||||
archive = ARCHIVE (archive_load (FALSE));
|
||||
archiver_db->archive = Bonobo_Moniker_resolve (parent, options, "IDL:ConfigArchiver/Archive:1.0", ev);
|
||||
|
||||
if (BONOBO_EX (ev) || archiver_db->archive == CORBA_OBJECT_NIL) {
|
||||
g_critical ("Could not resolve parent moniker to an archive");
|
||||
bonobo_object_unref (BONOBO_OBJECT (archiver_db));
|
||||
return CORBA_OBJECT_NIL;
|
||||
}
|
||||
|
||||
if (location_id == NULL || *location_id == '\0')
|
||||
archiver_db->location = archive_get_current_location (archive);
|
||||
archiver_db->location = ConfigArchiver_Archive__get_currentLocation (archiver_db->archive, ev);
|
||||
else
|
||||
archiver_db->location = archive_get_location (archive, location_id);
|
||||
archiver_db->location = ConfigArchiver_Archive_getLocation (archiver_db->archive, location_id, ev);
|
||||
|
||||
if (archiver_db->location == NULL) {
|
||||
if (archiver_db->location == CORBA_OBJECT_NIL) {
|
||||
bonobo_object_unref (BONOBO_OBJECT (archiver_db));
|
||||
return CORBA_OBJECT_NIL;
|
||||
}
|
||||
|
||||
archiver_db->backend_id = g_strdup (backend_id);
|
||||
archiver_db->archive = archive;
|
||||
archiver_db->real_name = real_name;
|
||||
|
||||
archiver_db->doc = location_load_rollback_data
|
||||
(archiver_db->location, NULL, 0, archiver_db->backend_id, TRUE);
|
||||
archiver_db->doc = location_client_load_rollback_data
|
||||
(archiver_db->location, NULL, 0, archiver_db->backend_id, TRUE, ev);
|
||||
|
||||
if (archiver_db->doc == NULL) {
|
||||
gchar *filename;
|
||||
|
@ -736,7 +736,9 @@ bonobo_config_archiver_new (const char *backend_id, const char *location_id)
|
|||
|
||||
db = CORBA_Object_duplicate (BONOBO_OBJREF (archiver_db), NULL);
|
||||
|
||||
bonobo_url_register ("BONOBO_CONF:ARCHIVER", real_name, NULL, db, &ev);
|
||||
bonobo_url_register ("BONOBO_CONF:ARCHIVER", real_name, NULL, db, ev);
|
||||
|
||||
DEBUG_MSG ("Exit: %p", db);
|
||||
|
||||
return db;
|
||||
}
|
||||
|
|
|
@ -18,8 +18,7 @@
|
|||
#include <bonobo/bonobo-event-source.h>
|
||||
#include <bonobo/bonobo-property-bag.h>
|
||||
|
||||
#include "archive.h"
|
||||
#include "location.h"
|
||||
#include "archiver-client.h"
|
||||
|
||||
BEGIN_GNOME_DECLS
|
||||
|
||||
|
@ -49,21 +48,21 @@ typedef struct {
|
|||
typedef struct _BonoboConfigArchiver BonoboConfigArchiver;
|
||||
|
||||
struct _BonoboConfigArchiver {
|
||||
BonoboConfigDatabase base;
|
||||
|
||||
char *filename;
|
||||
FILE *fp;
|
||||
xmlDocPtr doc;
|
||||
DirData *dir;
|
||||
guint time_id;
|
||||
BonoboConfigDatabase base;
|
||||
|
||||
Archive *archive;
|
||||
Location *location;
|
||||
gchar *backend_id;
|
||||
gchar *real_name;
|
||||
char *filename;
|
||||
FILE *fp;
|
||||
xmlDocPtr doc;
|
||||
DirData *dir;
|
||||
guint time_id;
|
||||
|
||||
BonoboEventSource *es;
|
||||
BonoboPropertyBag *pb;
|
||||
ConfigArchiver_Archive archive;
|
||||
ConfigArchiver_Location location;
|
||||
gchar *backend_id;
|
||||
gchar *real_name;
|
||||
|
||||
BonoboEventSource *es;
|
||||
BonoboPropertyBag *pb;
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
|
@ -75,7 +74,11 @@ GtkType
|
|||
bonobo_config_archiver_get_type (void);
|
||||
|
||||
Bonobo_ConfigDatabase
|
||||
bonobo_config_archiver_new (const char *backend_id, const char *location_id);
|
||||
bonobo_config_archiver_new (Bonobo_Moniker parent,
|
||||
const Bonobo_ResolveOptions *options,
|
||||
const char *backend_id,
|
||||
const char *location_id,
|
||||
CORBA_Environment *ev);
|
||||
|
||||
END_GNOME_DECLS
|
||||
|
||||
|
|
|
@ -17,9 +17,14 @@
|
|||
#include <bonobo/bonobo-exception.h>
|
||||
|
||||
#include "bonobo-config-archiver.h"
|
||||
#include "archive.h"
|
||||
#include "util.h"
|
||||
|
||||
#define EX_SET_NOT_FOUND(ev) bonobo_exception_set (ev, ex_Bonobo_Moniker_InterfaceNotFound)
|
||||
|
||||
static Archive *user_archive = NULL;
|
||||
static Archive *global_archive = NULL;
|
||||
|
||||
/* parse_name
|
||||
*
|
||||
* Given a moniker with a backend id and (possibly) a location id encoded
|
||||
|
@ -52,16 +57,85 @@ parse_name (const gchar *name, gchar **backend_id, gchar **location)
|
|||
return TRUE;
|
||||
}
|
||||
|
||||
static Bonobo_Unknown
|
||||
archiver_resolve (BonoboMoniker *moniker,
|
||||
const Bonobo_ResolveOptions *options,
|
||||
const CORBA_char *requested_interface,
|
||||
CORBA_Environment *ev)
|
||||
static void
|
||||
archive_destroy_cb (Archive *archive)
|
||||
{
|
||||
Bonobo_Moniker parent;
|
||||
Bonobo_ConfigDatabase db, pdb = CORBA_OBJECT_NIL;
|
||||
const gchar *name;
|
||||
gchar *backend_id, *location;
|
||||
if (archive == global_archive)
|
||||
global_archive = NULL;
|
||||
else if (archive == user_archive)
|
||||
user_archive = NULL;
|
||||
}
|
||||
|
||||
static Bonobo_Unknown
|
||||
archive_resolve (BonoboMoniker *moniker,
|
||||
const Bonobo_ResolveOptions *options,
|
||||
const CORBA_char *requested_interface,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
const gchar *name;
|
||||
|
||||
Bonobo_Unknown ret;
|
||||
|
||||
DEBUG_MSG ("Enter");
|
||||
|
||||
if (strcmp (requested_interface, "IDL:ConfigArchiver/Archive:1.0")) {
|
||||
EX_SET_NOT_FOUND (ev);
|
||||
return CORBA_OBJECT_NIL;
|
||||
}
|
||||
|
||||
name = bonobo_moniker_get_name (moniker);
|
||||
|
||||
if (!strcmp (name, "global-archive")) {
|
||||
DEBUG_MSG ("Global archive requested");
|
||||
|
||||
if (global_archive == NULL) {
|
||||
global_archive = ARCHIVE (archive_load (TRUE));
|
||||
gtk_signal_connect (GTK_OBJECT (global_archive), "destroy", GTK_SIGNAL_FUNC (archive_destroy_cb), NULL);
|
||||
ret = CORBA_Object_duplicate (BONOBO_OBJREF (global_archive), ev);
|
||||
} else {
|
||||
ret = bonobo_object_dup_ref (BONOBO_OBJREF (global_archive), ev);
|
||||
}
|
||||
|
||||
if (BONOBO_EX (ev)) {
|
||||
g_critical ("Cannot duplicate object");
|
||||
bonobo_object_release_unref (ret, NULL);
|
||||
ret = CORBA_OBJECT_NIL;
|
||||
}
|
||||
}
|
||||
else if (!strcmp (name, "user-archive")) {
|
||||
if (user_archive == NULL) {
|
||||
user_archive = ARCHIVE (archive_load (FALSE));
|
||||
gtk_signal_connect (GTK_OBJECT (user_archive), "destroy", GTK_SIGNAL_FUNC (archive_destroy_cb), NULL);
|
||||
ret = CORBA_Object_duplicate (BONOBO_OBJREF (user_archive), ev);
|
||||
} else {
|
||||
ret = bonobo_object_dup_ref (BONOBO_OBJREF (user_archive), ev);
|
||||
}
|
||||
|
||||
if (BONOBO_EX (ev)) {
|
||||
g_critical ("Cannot duplicate object");
|
||||
bonobo_object_release_unref (ret, NULL);
|
||||
ret = CORBA_OBJECT_NIL;
|
||||
}
|
||||
} else {
|
||||
EX_SET_NOT_FOUND (ev);
|
||||
ret = CORBA_OBJECT_NIL;
|
||||
}
|
||||
|
||||
DEBUG_MSG ("Exit");
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static Bonobo_Unknown
|
||||
archiverdb_resolve (BonoboMoniker *moniker,
|
||||
const Bonobo_ResolveOptions *options,
|
||||
const CORBA_char *requested_interface,
|
||||
CORBA_Environment *ev)
|
||||
{
|
||||
Bonobo_Moniker parent;
|
||||
Bonobo_ConfigDatabase db;
|
||||
const gchar *name;
|
||||
gchar *backend_id, *locid;
|
||||
|
||||
if (strcmp (requested_interface, "IDL:Bonobo/ConfigDatabase:1.0")) {
|
||||
EX_SET_NOT_FOUND (ev);
|
||||
|
@ -72,42 +146,27 @@ archiver_resolve (BonoboMoniker *moniker,
|
|||
if (BONOBO_EX (ev))
|
||||
return CORBA_OBJECT_NIL;
|
||||
|
||||
name = bonobo_moniker_get_name (moniker);
|
||||
|
||||
if (parent != CORBA_OBJECT_NIL) {
|
||||
pdb = Bonobo_Moniker_resolve (parent, options,
|
||||
"IDL:Bonobo/ConfigDatabase:1.0", ev);
|
||||
|
||||
bonobo_object_release_unref (parent, NULL);
|
||||
|
||||
if (BONOBO_EX (ev) || pdb == CORBA_OBJECT_NIL)
|
||||
return CORBA_OBJECT_NIL;
|
||||
}
|
||||
|
||||
if (parse_name (name, &backend_id, &location) < 0) {
|
||||
if (parent == CORBA_OBJECT_NIL) {
|
||||
EX_SET_NOT_FOUND (ev);
|
||||
return CORBA_OBJECT_NIL;
|
||||
}
|
||||
|
||||
if (!(db = bonobo_config_archiver_new (backend_id, location))) {
|
||||
g_free (backend_id);
|
||||
g_free (location);
|
||||
name = bonobo_moniker_get_name (moniker);
|
||||
|
||||
if (parse_name (name, &backend_id, &locid) < 0) {
|
||||
EX_SET_NOT_FOUND (ev);
|
||||
return CORBA_OBJECT_NIL;
|
||||
return CORBA_OBJECT_NIL;
|
||||
}
|
||||
|
||||
db = bonobo_config_archiver_new (parent, options, backend_id, locid, ev);
|
||||
|
||||
bonobo_object_release_unref (parent, NULL);
|
||||
|
||||
if (db == CORBA_OBJECT_NIL || BONOBO_EX (ev))
|
||||
EX_SET_NOT_FOUND (ev);
|
||||
|
||||
g_free (backend_id);
|
||||
g_free (location);
|
||||
|
||||
if (pdb != CORBA_OBJECT_NIL) {
|
||||
Bonobo_ConfigDatabase_addDatabase (db, pdb, "", Bonobo_ConfigDatabase_DEFAULT, ev);
|
||||
|
||||
if (BONOBO_EX (ev)) {
|
||||
bonobo_object_release_unref (pdb, NULL);
|
||||
bonobo_object_release_unref (db, NULL);
|
||||
return CORBA_OBJECT_NIL;
|
||||
}
|
||||
}
|
||||
g_free (locid);
|
||||
|
||||
return db;
|
||||
}
|
||||
|
@ -118,13 +177,16 @@ bonobo_moniker_archiver_factory (BonoboGenericFactory *this,
|
|||
const char *object_id,
|
||||
void *closure)
|
||||
{
|
||||
if (!strcmp (object_id, "OAFIID:Bonobo_Moniker_archiver")) {
|
||||
|
||||
return BONOBO_OBJECT (bonobo_moniker_simple_new (
|
||||
"archiver:", archiver_resolve));
|
||||
|
||||
} else
|
||||
if (!strcmp (object_id, "OAFIID:Bonobo_Moniker_archiverdb")) {
|
||||
return BONOBO_OBJECT (bonobo_moniker_simple_new
|
||||
("archiverdb:", archiverdb_resolve));
|
||||
}
|
||||
else if (!strcmp (object_id, "OAFIID:Bonobo_Moniker_archive")) {
|
||||
return BONOBO_OBJECT (bonobo_moniker_simple_new
|
||||
("archive:", archive_resolve));
|
||||
} else {
|
||||
g_warning ("Failing to manufacture a '%s'", object_id);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
|
438
archiver/config-archiver.c
Normal file
438
archiver/config-archiver.c
Normal file
|
@ -0,0 +1,438 @@
|
|||
/* -*- mode: c; style: linux -*- */
|
||||
|
||||
/* main.c
|
||||
* Copyright (C) 2000-2001 Ximian, Inc.
|
||||
*
|
||||
* Written by Bradford Hovinen (hovinen@ximian.com)
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2, 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 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.
|
||||
*/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include <stdio.h>
|
||||
#include <time.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/file.h>
|
||||
#include <unistd.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include <gnome.h>
|
||||
#include <bonobo.h>
|
||||
|
||||
#include <gnome-xml/parser.h>
|
||||
|
||||
#include "archiver-client.h"
|
||||
#include "util.h"
|
||||
|
||||
/* Variables resulting from command line parsing */
|
||||
|
||||
static gboolean store;
|
||||
static gboolean rollback;
|
||||
static gboolean change_location;
|
||||
static gboolean rename_location;
|
||||
static gboolean push_config;
|
||||
static gboolean garbage_collect;
|
||||
|
||||
static gboolean add_location;
|
||||
static gboolean remove_location;
|
||||
static gboolean add_backend;
|
||||
static gboolean remove_backend;
|
||||
|
||||
static gboolean global;
|
||||
static const gchar *location_id;
|
||||
|
||||
static gchar *backend_id;
|
||||
|
||||
static gboolean compare_parent;
|
||||
static gboolean mask_previous;
|
||||
|
||||
static gchar *date_str;
|
||||
static gboolean all;
|
||||
static gchar *revision_id;
|
||||
static gboolean last;
|
||||
static guint steps;
|
||||
static gboolean show;
|
||||
|
||||
static gchar *parent_str;
|
||||
static gchar *new_name;
|
||||
|
||||
static gboolean contain_full;
|
||||
static gboolean contain_partial;
|
||||
static gboolean master;
|
||||
|
||||
static struct poptOption archiver_operations[] = {
|
||||
{"store", 's', POPT_ARG_NONE, &store, 0,
|
||||
N_("Store XML data in the archive")},
|
||||
{"rollback", 'r', POPT_ARG_NONE, &rollback, 0,
|
||||
N_("Roll back the configuration to a given point")},
|
||||
{"change-location", 'c', POPT_ARG_NONE, &change_location, 0,
|
||||
N_("Change the location profile to the given one")},
|
||||
{"push-config", 'p', POPT_ARG_NONE, &push_config, 0,
|
||||
N_("Push configuration data out to client machines (UNIMPLEMENTED)")},
|
||||
{"rename-location", '\0', POPT_ARG_NONE, &rename_location, 0,
|
||||
N_("Rename a location to a new name")},
|
||||
{"add-location", '\0', POPT_ARG_NONE, &add_location, 0,
|
||||
N_("Add a new location to the archive")},
|
||||
{"remove-location", '\0', POPT_ARG_NONE, &remove_location, 0,
|
||||
N_("Remove a location from the archive")},
|
||||
{"add-backend", '\0', POPT_ARG_NONE, &add_backend, 0,
|
||||
N_("Add a given backend to the given location")},
|
||||
{"remove-backend", '\0', POPT_ARG_NONE, &remove_backend, 0,
|
||||
N_("Remove the given backend from the given location")},
|
||||
{"garbage-collect", '\0', POPT_ARG_NONE, &garbage_collect, 0,
|
||||
N_("Perform garbage collection on the given location")},
|
||||
{NULL, '\0', 0, NULL, 0}
|
||||
};
|
||||
|
||||
static struct poptOption global_options[] = {
|
||||
{"global", 'g', POPT_ARG_NONE, &global, 0,
|
||||
N_("Use the global repository")},
|
||||
{"location", 'l', POPT_ARG_STRING, &location_id, 0,
|
||||
N_("Identifier of location profile on which to operate"),
|
||||
N_("LOCATION")},
|
||||
{"backend", 'b', POPT_ARG_STRING, &backend_id, 0,
|
||||
N_("Backend being used for this operation"), N_("BACKEND_ID")},
|
||||
{NULL, '\0', 0, NULL, 0}
|
||||
};
|
||||
|
||||
static struct poptOption store_options[] = {
|
||||
{"compare-parent", '\0', POPT_ARG_NONE, &compare_parent, 0,
|
||||
N_("Store only the differences with the parent location's config")},
|
||||
{"mask-previous", '\0', POPT_ARG_NONE, &mask_previous, 0,
|
||||
N_("Store only those settings set in the previous config")},
|
||||
{NULL, '\0', 0, NULL, 0}
|
||||
};
|
||||
|
||||
static struct poptOption rollback_options[] = {
|
||||
{"date", 'd', POPT_ARG_STRING, &date_str, 0,
|
||||
N_("Date to which to roll back"), N_("DATE")},
|
||||
{"all", 'a', POPT_ARG_NONE, &all, 0,
|
||||
N_("Roll back all configuration items")},
|
||||
{"revision-id", 'i', POPT_ARG_INT, &revision_id, 0,
|
||||
N_("Roll back to the revision REVISION_ID"), N_("REVISION_ID")},
|
||||
{"last", 't', POPT_ARG_NONE, &last, 0,
|
||||
N_("Roll back to the last known revision")},
|
||||
{"steps", '\0', POPT_ARG_INT, &steps, 0,
|
||||
N_("Roll back by STEPS revisions"), N_("STEPS")},
|
||||
{"show", 'h', POPT_ARG_NONE, &show, 0,
|
||||
N_("Don't run the backend, just dump the output")},
|
||||
{NULL, '\0', 0, NULL, 0}
|
||||
};
|
||||
|
||||
static struct poptOption add_rename_location_options[] = {
|
||||
{"parent", '\0', POPT_ARG_STRING, &parent_str, 0,
|
||||
N_("Parent location for the new location"), N_("PARENT")},
|
||||
{"new-name", '\0', POPT_ARG_STRING, &new_name, 0,
|
||||
N_("New name to assign to the location"), N_("NEW_NAME")},
|
||||
{NULL, '\0', 0, NULL, 0}
|
||||
};
|
||||
|
||||
static struct poptOption add_remove_backend_options[] = {
|
||||
{"master", '\0', POPT_ARG_NONE, &master, 0,
|
||||
N_("Add/remove this backend to/from the master backend list")},
|
||||
{"full", '\0', POPT_ARG_NONE, &contain_full, 0,
|
||||
N_("Full containment")},
|
||||
{"partial", '\0', POPT_ARG_NONE, &contain_partial, 0,
|
||||
N_("Partial containment")},
|
||||
{NULL, '\0', 0, NULL, 0}
|
||||
};
|
||||
|
||||
static xmlDocPtr
|
||||
xml_load_from_stream (FILE *stream)
|
||||
{
|
||||
GString *str;
|
||||
gchar buffer[4097];
|
||||
xmlDocPtr doc;
|
||||
size_t t;
|
||||
|
||||
str = g_string_new ("");
|
||||
|
||||
while (!feof (stream)) {
|
||||
t = fread (buffer, sizeof (char), 4096, stream);
|
||||
buffer[t] = '\0';
|
||||
g_string_append (str, buffer);
|
||||
}
|
||||
|
||||
doc = xmlParseDoc (str->str);
|
||||
g_string_free (str, TRUE);
|
||||
return doc;
|
||||
}
|
||||
|
||||
static ConfigArchiver_StringSeq *
|
||||
make_backend_id_seq (gchar *backend_id, ...)
|
||||
{
|
||||
ConfigArchiver_StringSeq *seq;
|
||||
|
||||
seq = ConfigArchiver_StringSeq__alloc ();
|
||||
seq->_length = 1;
|
||||
seq->_buffer = CORBA_sequence_CORBA_string_allocbuf (1);
|
||||
seq->_buffer[0] = CORBA_string_dup (backend_id);
|
||||
|
||||
return seq;
|
||||
}
|
||||
|
||||
static void
|
||||
do_store (ConfigArchiver_Location location, CORBA_Environment *ev)
|
||||
{
|
||||
ConfigArchiver_StoreType type;
|
||||
xmlDocPtr doc;
|
||||
|
||||
if (!backend_id) {
|
||||
fprintf (stderr, "No backend specified\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (mask_previous)
|
||||
type = ConfigArchiver_STORE_MASK_PREVIOUS;
|
||||
else if (compare_parent)
|
||||
type = ConfigArchiver_STORE_COMPARE_PARENT;
|
||||
else
|
||||
type = ConfigArchiver_STORE_FULL;
|
||||
|
||||
doc = xml_load_from_stream (stdin);
|
||||
|
||||
location_client_store_xml (location, backend_id, doc, type, ev);
|
||||
}
|
||||
|
||||
static void
|
||||
do_rollback (ConfigArchiver_Location location, CORBA_Environment *ev)
|
||||
{
|
||||
struct tm *date = NULL;
|
||||
ConfigArchiver_StringSeq *seq;
|
||||
ConfigArchiver_Time tm;
|
||||
xmlDocPtr doc;
|
||||
|
||||
if (date_str)
|
||||
date = parse_date (date_str);
|
||||
else if (last || steps > 0)
|
||||
date = NULL;
|
||||
else if (!revision_id) {
|
||||
fprintf (stderr, "No date specified\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (backend_id != NULL && (date != NULL || last)) {
|
||||
/* FIXME: Need to support specifying multiple backends */
|
||||
if (show) {
|
||||
doc = location_client_load_rollback_data (location, date, 0, backend_id, TRUE, ev);
|
||||
xmlDocDump (stdout, doc);
|
||||
xmlFreeDoc (doc);
|
||||
} else {
|
||||
tm = mktime (date);
|
||||
seq = make_backend_id_seq (backend_id, NULL);
|
||||
ConfigArchiver_Location_rollbackBackends (location, tm, 0, seq, TRUE, ev);
|
||||
CORBA_free (seq);
|
||||
}
|
||||
}
|
||||
else if (backend_id != NULL && steps != 0) {
|
||||
if (show) {
|
||||
doc = location_client_load_rollback_data (location, date, steps, backend_id, TRUE, ev);
|
||||
xmlDocDump (stdout, doc);
|
||||
xmlFreeDoc (doc);
|
||||
} else {
|
||||
seq = make_backend_id_seq (backend_id, NULL);
|
||||
ConfigArchiver_Location_rollbackBackends (location, 0, steps, seq, TRUE, ev);
|
||||
CORBA_free (seq);
|
||||
}
|
||||
} else {
|
||||
g_message ("No backend specified\n");
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
do_change_location (ConfigArchiver_Archive archive, ConfigArchiver_Location location, CORBA_Environment *ev)
|
||||
{
|
||||
ConfigArchiver_Archive__set_currentLocation (archive, location, ev);
|
||||
}
|
||||
|
||||
static void
|
||||
do_rename_location (ConfigArchiver_Archive archive, ConfigArchiver_Location location, CORBA_Environment *ev)
|
||||
{
|
||||
gboolean is_current;
|
||||
CORBA_char *locid, *cid;
|
||||
|
||||
if (new_name == NULL) {
|
||||
fprintf (stderr, "You did not specify a new name. Try --help\n");
|
||||
} else {
|
||||
locid = ConfigArchiver_Location__get_id (location, ev);
|
||||
cid = ConfigArchiver_Archive__get_currentLocationId (archive, ev);
|
||||
|
||||
if (!strcmp (locid, cid))
|
||||
is_current = TRUE;
|
||||
else
|
||||
is_current = FALSE;
|
||||
|
||||
CORBA_free (locid);
|
||||
CORBA_free (cid);
|
||||
|
||||
ConfigArchiver_Location__set_id (location, new_name, ev);
|
||||
|
||||
if (is_current)
|
||||
ConfigArchiver_Archive__set_currentLocationId (archive, new_name, ev);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
do_add_location (ConfigArchiver_Archive archive, CORBA_Environment *ev)
|
||||
{
|
||||
ConfigArchiver_Location parent_location = CORBA_OBJECT_NIL;
|
||||
|
||||
if (location_id == NULL) {
|
||||
fprintf (stderr, "Error: You did not specify a location name\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (parent_str != NULL) {
|
||||
parent_location = ConfigArchiver_Archive_getLocation (archive, parent_str, ev);
|
||||
|
||||
if (parent_location == NULL && !strcmp (parent_str, "default"))
|
||||
parent_location =
|
||||
ConfigArchiver_Archive_createLocation (archive, "default", _("Default Location"),
|
||||
CORBA_OBJECT_NIL, ev);
|
||||
}
|
||||
|
||||
ConfigArchiver_Archive_createLocation (archive, location_id, location_id, parent_location, ev);
|
||||
}
|
||||
|
||||
static void
|
||||
do_remove_location (ConfigArchiver_Location location, CORBA_Environment *ev)
|
||||
{
|
||||
ConfigArchiver_Location_delete (location, ev);
|
||||
}
|
||||
|
||||
static void
|
||||
do_add_backend (ConfigArchiver_Location location, CORBA_Environment *ev)
|
||||
{
|
||||
ConfigArchiver_ContainmentType type;
|
||||
|
||||
if (contain_full && contain_partial) {
|
||||
fprintf (stderr, "Error: Cannot have both full and partial "
|
||||
"containment\n");
|
||||
return;
|
||||
}
|
||||
else if (contain_partial) {
|
||||
type = ConfigArchiver_CONTAIN_PARTIAL;
|
||||
} else {
|
||||
type = ConfigArchiver_CONTAIN_FULL;
|
||||
}
|
||||
|
||||
ConfigArchiver_Location_addBackend (location, backend_id, type, ev);
|
||||
}
|
||||
|
||||
static void
|
||||
do_remove_backend (ConfigArchiver_Location location, CORBA_Environment *ev)
|
||||
{
|
||||
ConfigArchiver_Location_removeBackend (location, backend_id, ev);
|
||||
}
|
||||
|
||||
static void
|
||||
do_garbage_collect (ConfigArchiver_Location location, CORBA_Environment *ev)
|
||||
{
|
||||
ConfigArchiver_Location_garbageCollect (location, ev);
|
||||
}
|
||||
|
||||
int
|
||||
main (int argc, char **argv)
|
||||
{
|
||||
CORBA_ORB orb;
|
||||
ConfigArchiver_Archive archive;
|
||||
ConfigArchiver_Location location = CORBA_OBJECT_NIL;
|
||||
CORBA_Environment ev;
|
||||
|
||||
/* For Electric Fence */
|
||||
free (malloc (1));
|
||||
|
||||
bindtextdomain (PACKAGE, GNOMELOCALEDIR);
|
||||
textdomain (PACKAGE);
|
||||
|
||||
CORBA_exception_init (&ev);
|
||||
|
||||
gnomelib_register_popt_table (global_options,
|
||||
_("Global archiver options"));
|
||||
gnomelib_register_popt_table (archiver_operations,
|
||||
_("Archiver commands"));
|
||||
gnomelib_register_popt_table (store_options,
|
||||
_("Options for storing data"));
|
||||
gnomelib_register_popt_table (rollback_options,
|
||||
_("Options for rolling back"));
|
||||
gnomelib_register_popt_table (add_rename_location_options,
|
||||
_("Options for adding or renaming " \
|
||||
"locations"));
|
||||
gnomelib_register_popt_table (add_remove_backend_options,
|
||||
_("Options for adding and removing " \
|
||||
"backends"));
|
||||
|
||||
gtk_type_init ();
|
||||
gnomelib_init ("archiver", VERSION);
|
||||
gnomelib_parse_args (argc, argv, 0);
|
||||
|
||||
orb = oaf_init (argc, argv);
|
||||
|
||||
if (bonobo_init (orb, CORBA_OBJECT_NIL, CORBA_OBJECT_NIL) == FALSE)
|
||||
g_error ("Cannot initialize Bonobo");
|
||||
|
||||
if (global)
|
||||
archive = bonobo_get_object ("archive:global-archive", "IDL:ConfigArchiver/Archive:1.0", &ev);
|
||||
else
|
||||
archive = bonobo_get_object ("archive:user-archive", "IDL:ConfigArchiver/Archive:1.0", &ev);
|
||||
|
||||
if (archive == CORBA_OBJECT_NIL) {
|
||||
g_critical ("Could not open archive\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (!add_location) {
|
||||
if (location_id == NULL)
|
||||
location_id = ConfigArchiver_Archive__get_currentLocationId (archive, &ev);
|
||||
|
||||
location = ConfigArchiver_Archive_getLocation (archive, location_id, &ev);
|
||||
|
||||
if (location == CORBA_OBJECT_NIL) {
|
||||
g_critical ("Error: Could not open location %s\n", location_id);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
if (store)
|
||||
do_store (location, &ev);
|
||||
else if (rollback)
|
||||
do_rollback (location, &ev);
|
||||
else if (change_location)
|
||||
do_change_location (archive, location, &ev);
|
||||
else if (rename_location)
|
||||
do_rename_location (archive, location, &ev);
|
||||
else if (add_location)
|
||||
do_add_location (archive, &ev);
|
||||
else if (remove_location)
|
||||
do_remove_location (location, &ev);
|
||||
else if (add_backend)
|
||||
do_add_backend (location, &ev);
|
||||
else if (remove_backend)
|
||||
do_remove_backend (location, &ev);
|
||||
else if (garbage_collect)
|
||||
do_garbage_collect (location, &ev);
|
||||
|
||||
bonobo_object_release_unref (archive, NULL);
|
||||
|
||||
if (location != CORBA_OBJECT_NIL)
|
||||
bonobo_object_release_unref (location, NULL);
|
||||
|
||||
return 0;
|
||||
}
|
|
@ -89,7 +89,7 @@ static GList *find_config_log_entry_date (ConfigLog *config_log,
|
|||
struct tm *date);
|
||||
static GList *find_config_log_entry_backend (ConfigLog *config_log,
|
||||
GList *start,
|
||||
gchar *backend_id);
|
||||
const gchar *backend_id);
|
||||
|
||||
static GList *load_log_entry (ConfigLog *config_log,
|
||||
GList *last);
|
||||
|
@ -300,7 +300,7 @@ config_log_delete (ConfigLog *config_log)
|
|||
gint
|
||||
config_log_get_rollback_id_for_date (ConfigLog *config_log,
|
||||
struct tm *date,
|
||||
gchar *backend_id)
|
||||
const gchar *backend_id)
|
||||
{
|
||||
GList *node;
|
||||
|
||||
|
@ -333,7 +333,8 @@ config_log_get_rollback_id_for_date (ConfigLog *config_log,
|
|||
|
||||
gint
|
||||
config_log_get_rollback_id_by_steps (ConfigLog *config_log,
|
||||
guint steps, gchar *backend_id)
|
||||
guint steps,
|
||||
const gchar *backend_id)
|
||||
{
|
||||
GList *node;
|
||||
|
||||
|
@ -394,7 +395,7 @@ config_log_get_backend_id_for_id (ConfigLog *config_log, gint id)
|
|||
|
||||
/* Return the date the data with the given id was written */
|
||||
|
||||
struct tm *
|
||||
const struct tm *
|
||||
config_log_get_date_for_id (ConfigLog *config_log, gint id)
|
||||
{
|
||||
GList *node;
|
||||
|
@ -429,8 +430,9 @@ config_log_get_date_for_id (ConfigLog *config_log, gint id)
|
|||
**/
|
||||
|
||||
gint
|
||||
config_log_write_entry (ConfigLog *config_log, gchar *backend_id,
|
||||
gboolean is_default_data)
|
||||
config_log_write_entry (ConfigLog *config_log,
|
||||
const gchar *backend_id,
|
||||
gboolean is_default_data)
|
||||
{
|
||||
ConfigLogEntry *entry;
|
||||
|
||||
|
@ -454,9 +456,6 @@ config_log_write_entry (ConfigLog *config_log, gchar *backend_id,
|
|||
g_list_prepend (config_log->p->log_data, entry);
|
||||
|
||||
dump_log (config_log);
|
||||
if (config_log->p->file_stream != NULL)
|
||||
fclose (config_log->p->file_stream);
|
||||
do_load (config_log);
|
||||
|
||||
return entry->id;
|
||||
}
|
||||
|
@ -565,6 +564,7 @@ config_log_garbage_collect (ConfigLog *config_log,
|
|||
GList *node, *list = NULL;
|
||||
ConfigLogEntry *e1, *e2;
|
||||
time_t t1, t2, now;
|
||||
struct tm now_b, *tmp_date;
|
||||
|
||||
g_return_if_fail (config_log != NULL);
|
||||
g_return_if_fail (IS_CONFIG_LOG (config_log));
|
||||
|
@ -593,15 +593,27 @@ config_log_garbage_collect (ConfigLog *config_log,
|
|||
if (list == NULL) return;
|
||||
|
||||
now = time (NULL);
|
||||
gmtime_r (&now, &now_b);
|
||||
now = mktime (&now_b);
|
||||
|
||||
for (node = list; node->next != NULL; node = node->next) {
|
||||
e1 = ((GList *) node->data)->data;
|
||||
e2 = ((GList *) node->next->data)->data;
|
||||
|
||||
t1 = mktime (e1->date);
|
||||
t2 = mktime (e2->date);
|
||||
tmp_date = dup_date (e1->date);
|
||||
t1 = mktime (tmp_date);
|
||||
g_free (tmp_date);
|
||||
|
||||
if (K_CONST * (t2 - t1) < now - t2) {
|
||||
tmp_date = dup_date (e2->date);
|
||||
t2 = mktime (tmp_date);
|
||||
g_free (tmp_date);
|
||||
|
||||
if (now < t2 || now < t1)
|
||||
g_warning ("Log entry is in the future!");
|
||||
if (t1 > t2)
|
||||
g_warning ("Log entries are out of order!");
|
||||
|
||||
if (K_CONST * difftime (t2, t1) < difftime (now, t2)) {
|
||||
config_log->p->log_data =
|
||||
g_list_remove_link (config_log->p->log_data, node->data);
|
||||
callback (config_log, backend_id, e1->id, data);
|
||||
|
@ -693,8 +705,9 @@ find_config_log_entry_date (ConfigLog *config_log, GList *start,
|
|||
*/
|
||||
|
||||
static GList *
|
||||
find_config_log_entry_backend (ConfigLog *config_log, GList *start,
|
||||
gchar *backend_id)
|
||||
find_config_log_entry_backend (ConfigLog *config_log,
|
||||
GList *start,
|
||||
const gchar *backend_id)
|
||||
{
|
||||
GList *last;
|
||||
ConfigLogEntry *entry;
|
||||
|
@ -812,6 +825,9 @@ parse_line (char *buffer, int *id, struct tm *date, char **backend_id)
|
|||
if (extract_number (&buffer, &date->tm_sec, 2) == FALSE)
|
||||
return FALSE;
|
||||
|
||||
date->tm_gmtoff = 0;
|
||||
date->tm_zone = "GMT";
|
||||
|
||||
if (!isspace (*buffer) || *(buffer + 1) == '\0') return FALSE;
|
||||
buffer++;
|
||||
|
||||
|
@ -918,10 +934,10 @@ static struct tm *
|
|||
get_current_date (void)
|
||||
{
|
||||
time_t current_time;
|
||||
struct tm *time_1, *ret;
|
||||
struct tm time_2, *time_1 = &time_2, *ret;
|
||||
|
||||
current_time = time (NULL);
|
||||
time_1 = localtime (¤t_time);
|
||||
gmtime_r (¤t_time, time_1);
|
||||
ret = g_new (struct tm, 1);
|
||||
memcpy (ret, time_1, sizeof (struct tm));
|
||||
return ret;
|
||||
|
@ -952,7 +968,7 @@ dump_log (ConfigLog *config_log)
|
|||
{
|
||||
char *filename_out;
|
||||
GList *first;
|
||||
FILE *output;
|
||||
FILE *input, *output;
|
||||
|
||||
DEBUG_MSG ("Enter");
|
||||
|
||||
|
@ -983,8 +999,9 @@ dump_log (ConfigLog *config_log)
|
|||
((config_log->p->first_old == NULL && config_log->p->log_data == NULL) ||
|
||||
(config_log->p->first_old != NULL && config_log->p->log_data != NULL)))
|
||||
{
|
||||
rewind (config_log->p->file_stream);
|
||||
dump_file (config_log->p->file_stream, output);
|
||||
input = fopen (config_log->p->filename, "r");
|
||||
dump_file (input, output);
|
||||
fclose (input);
|
||||
}
|
||||
|
||||
config_log->p->first_old = config_log->p->log_data;
|
||||
|
|
|
@ -61,18 +61,18 @@ void config_log_delete (ConfigLog *config_log)
|
|||
|
||||
gint config_log_get_rollback_id_for_date (ConfigLog *config_log,
|
||||
struct tm *date,
|
||||
gchar *backend_id);
|
||||
const gchar *backend_id);
|
||||
gint config_log_get_rollback_id_by_steps (ConfigLog *config_log,
|
||||
guint steps,
|
||||
gchar *backend_id);
|
||||
const gchar *backend_id);
|
||||
|
||||
gchar *config_log_get_backend_id_for_id (ConfigLog *config_log,
|
||||
gint id);
|
||||
struct tm *config_log_get_date_for_id (ConfigLog *config_log,
|
||||
const struct tm *config_log_get_date_for_id (ConfigLog *config_log,
|
||||
gint id);
|
||||
|
||||
gint config_log_write_entry (ConfigLog *config_log,
|
||||
gchar *backend_id,
|
||||
const gchar *backend_id,
|
||||
gboolean is_default_data);
|
||||
|
||||
void config_log_iterate (ConfigLog *config_log,
|
||||
|
|
1192
archiver/location.c
1192
archiver/location.c
File diff suppressed because it is too large
Load diff
|
@ -26,6 +26,9 @@
|
|||
|
||||
#include <gnome.h>
|
||||
#include <tree.h>
|
||||
#include <bonobo.h>
|
||||
|
||||
#include "ConfigArchiver.h"
|
||||
|
||||
#include "config-log.h"
|
||||
|
||||
|
@ -37,118 +40,100 @@ typedef struct _LocationClass LocationClass;
|
|||
typedef struct _LocationPrivate LocationPrivate;
|
||||
typedef struct _Archive Archive;
|
||||
|
||||
typedef enum _ContainmentType ContainmentType;
|
||||
typedef enum _StoreType StoreType;
|
||||
typedef ConfigArchiver_ContainmentType ContainmentType;
|
||||
typedef ConfigArchiver_StoreType StoreType;
|
||||
|
||||
typedef int (*LocationBackendCB) (Location *, gchar *, gpointer);
|
||||
|
||||
struct _Location
|
||||
{
|
||||
GtkObject object;
|
||||
BonoboXObject object;
|
||||
|
||||
LocationPrivate *p;
|
||||
};
|
||||
|
||||
struct _LocationClass
|
||||
{
|
||||
GtkObjectClass parent;
|
||||
BonoboXObjectClass parent;
|
||||
|
||||
POA_ConfigArchiver_Location__epv epv;
|
||||
|
||||
gboolean (*do_rollback) (Location *location,
|
||||
gchar *backend_id,
|
||||
xmlDocPtr xml_doc);
|
||||
};
|
||||
|
||||
enum _ContainmentType
|
||||
{
|
||||
CONTAIN_NONE, CONTAIN_PARTIAL, CONTAIN_FULL
|
||||
};
|
||||
guint location_get_type (void);
|
||||
|
||||
enum _StoreType
|
||||
{
|
||||
STORE_DEFAULT, STORE_FULL, STORE_COMPARE_PARENT, STORE_MASK_PREVIOUS
|
||||
};
|
||||
BonoboObject *location_new (Archive *archive,
|
||||
const gchar *locid,
|
||||
const gchar *label,
|
||||
Location *parent);
|
||||
BonoboObject *location_open (Archive *archive,
|
||||
const gchar *locid);
|
||||
|
||||
guint location_get_type (void);
|
||||
void location_delete (Location *location);
|
||||
|
||||
GtkObject *location_new (Archive *archive,
|
||||
const gchar *locid,
|
||||
Location *inherits);
|
||||
GtkObject *location_open (Archive *archive,
|
||||
const gchar *locid);
|
||||
gchar *location_get_storage_filename (Location *location,
|
||||
const gchar *backend_id,
|
||||
gboolean is_default);
|
||||
gchar *location_get_rollback_filename (Location *location,
|
||||
struct tm *date,
|
||||
gint steps,
|
||||
const gchar *backend_id,
|
||||
gboolean parent_chain);
|
||||
|
||||
void location_close (Location *location);
|
||||
void location_delete (Location *location);
|
||||
gint location_store (Location *location,
|
||||
gchar *backend_id,
|
||||
FILE *input,
|
||||
ConfigArchiver_StoreType store_type);
|
||||
void location_store_xml (Location *location,
|
||||
gchar *backend_id,
|
||||
xmlDocPtr xml_doc,
|
||||
ConfigArchiver_StoreType store_type);
|
||||
|
||||
gint location_store (Location *location,
|
||||
gchar *backend_id,
|
||||
FILE *input,
|
||||
StoreType store_type);
|
||||
void location_store_xml (Location *location,
|
||||
gchar *backend_id,
|
||||
xmlDocPtr xml_doc,
|
||||
StoreType store_type);
|
||||
void location_rollback_backends_to (Location *location,
|
||||
struct tm *date,
|
||||
gint steps,
|
||||
GList *backends,
|
||||
gboolean parent_chain);
|
||||
|
||||
void location_rollback_backend_to (Location *location,
|
||||
struct tm *date,
|
||||
gchar *backend_id,
|
||||
gboolean parent_chain);
|
||||
void location_rollback_backends_to (Location *location,
|
||||
struct tm *date,
|
||||
GList *backends,
|
||||
gboolean parent_chain);
|
||||
void location_rollback_all_to (Location *location,
|
||||
struct tm *date,
|
||||
gboolean parent_chain);
|
||||
const struct tm *location_get_modification_time (Location *location,
|
||||
const gchar *backend_id);
|
||||
|
||||
void location_rollback_backend_by (Location *location,
|
||||
guint steps,
|
||||
gchar *backend_id,
|
||||
gboolean parent_chain);
|
||||
ContainmentType location_contains (Location *location,
|
||||
const gchar *backend_id);
|
||||
gint location_add_backend (Location *location,
|
||||
const gchar *backend_id,
|
||||
ContainmentType type);
|
||||
void location_remove_backend (Location *location,
|
||||
const gchar *backend_id);
|
||||
|
||||
void location_rollback_id (Location *location,
|
||||
gint id);
|
||||
void location_foreach_backend (Location *location,
|
||||
LocationBackendCB callback,
|
||||
gpointer data);
|
||||
|
||||
void location_dump_rollback_data (Location *location,
|
||||
struct tm *date,
|
||||
guint steps,
|
||||
gchar *backend_id,
|
||||
gboolean parent_chain,
|
||||
FILE *output);
|
||||
xmlDocPtr location_load_rollback_data (Location *location,
|
||||
struct tm *date,
|
||||
guint steps,
|
||||
gchar *backend_id,
|
||||
gboolean parent_chain);
|
||||
GList *location_find_path_from_common_parent (Location *location,
|
||||
Location *location2);
|
||||
|
||||
ContainmentType location_contains (Location *location, gchar *backend_id);
|
||||
gint location_add_backend (Location *location, gchar *backend_id,
|
||||
ContainmentType type);
|
||||
void location_remove_backend (Location *location, gchar *backend_id);
|
||||
Location *location_get_parent (Location *location);
|
||||
const gchar *location_get_path (Location *location);
|
||||
const gchar *location_get_label (Location *location);
|
||||
const gchar *location_get_id (Location *location);
|
||||
|
||||
void location_foreach_backend (Location *location,
|
||||
LocationBackendCB callback,
|
||||
gpointer data);
|
||||
void location_set_id (Location *location,
|
||||
const gchar *locid);
|
||||
|
||||
GList *location_find_path_from_common_parent (Location *location,
|
||||
Location *location2);
|
||||
gint location_store_full_snapshot (Location *location);
|
||||
|
||||
Location *location_get_parent (Location *location);
|
||||
const gchar *location_get_path (Location *location);
|
||||
const gchar *location_get_label (Location *location);
|
||||
const gchar *location_get_id (Location *location);
|
||||
GList *location_get_changed_backends (Location *location,
|
||||
Location *location1);
|
||||
gboolean location_does_backend_change (Location *location,
|
||||
Location *location1,
|
||||
const gchar *backend_id);
|
||||
|
||||
void location_set_id (Location *location, const gchar *locid);
|
||||
ConfigLog *location_get_config_log (Location *location);
|
||||
|
||||
gint location_store_full_snapshot (Location *location);
|
||||
|
||||
GList *location_get_changed_backends (Location *location,
|
||||
Location *location1);
|
||||
gboolean location_does_backend_change (Location *location,
|
||||
Location *location1,
|
||||
gchar *backend_id);
|
||||
|
||||
ConfigLog *location_get_config_log (Location *location);
|
||||
|
||||
void location_garbage_collect (Location *location);
|
||||
void location_garbage_collect (Location *location);
|
||||
|
||||
#endif /* __LOCATION */
|
||||
|
|
|
@ -95,3 +95,13 @@ parse_date (char *str)
|
|||
|
||||
return date;
|
||||
}
|
||||
|
||||
struct tm *
|
||||
dup_date (const struct tm *date)
|
||||
{
|
||||
struct tm *date1;
|
||||
|
||||
date1 = g_new (struct tm, 1);
|
||||
memcpy (date1, date, sizeof (struct tm));
|
||||
return date1;
|
||||
}
|
||||
|
|
|
@ -44,8 +44,8 @@
|
|||
# define DEBUG_MSG(str, args...)
|
||||
#endif
|
||||
|
||||
|
||||
gboolean extract_number (char **str, int *number, int digits);
|
||||
struct tm *parse_date (char *str);
|
||||
struct tm *dup_date (const struct tm *date);
|
||||
|
||||
#endif /* __UTIL_H */
|
||||
|
|
|
@ -1,3 +1,7 @@
|
|||
2001-08-20 Bradford Hovinen <hovinen@ximian.com>
|
||||
|
||||
* capplet-util.c (get_default_moniker): Update moniker being used
|
||||
|
||||
2001-07-30 Bradford Hovinen <hovinen@ximian.com>
|
||||
|
||||
* capplet-util.c (capplet_init): Don't sync if we need legacy
|
||||
|
|
|
@ -334,7 +334,7 @@ get_default_moniker (const gchar *binary)
|
|||
else tmp++;
|
||||
if ((tmp1 = strstr (tmp, "-capplet")) != NULL) *tmp1 = '\0';
|
||||
|
||||
res = g_strconcat ("archiver:", tmp, NULL);
|
||||
res = g_strconcat ("archive:user-archive#archiverdb:", tmp, NULL);
|
||||
g_free (s);
|
||||
return res;
|
||||
}
|
||||
|
|
|
@ -131,7 +131,7 @@ PKG_CHECK_MODULES(CAPPLET, $capplet_modules $PKG_BONOBO_CONF_CHECK)
|
|||
PKG_CHECK_MODULES(GNOMECC, gnomeui libglade xml gdk_pixbuf gnomecanvaspixbuf $PKG_BONOBO_CHECK gtkhtml >= 0.9)
|
||||
PKG_CHECK_MODULES(RMHELPER, gnomeui gnomecanvaspixbuf)
|
||||
PKG_CHECK_MODULES(ARCHIVER, $PKG_BONOBO_CONF_CHECK xml)
|
||||
PKG_CHECK_MODULES(CONFIG_ARCHIVER, gnome xml)
|
||||
PKG_CHECK_MODULES(CONFIG_ARCHIVER, bonobo gnome xml)
|
||||
|
||||
if test "x$moniker_enable" = "xyes"; then
|
||||
PKG_CHECK_MODULES(MONIKER, $PKG_BONOBO_CONF_CHECK xml)
|
||||
|
@ -276,6 +276,7 @@ capplets/screensaver/Makefile
|
|||
capplets/screensaver/screensavers/Makefile
|
||||
capplets/screensaver/screensavers/magic.pl
|
||||
capplets/sound/Makefile
|
||||
idl/Makefile
|
||||
intl/Makefile])
|
||||
echo "
|
||||
|
||||
|
@ -294,4 +295,3 @@ esac
|
|||
echo "
|
||||
|
||||
"
|
||||
|
||||
|
|
|
@ -1,3 +1,8 @@
|
|||
2001-08-20 Bradford Hovinen <hovinen@ximian.com>
|
||||
|
||||
* capplet-dir.c (capplet_control_launch): Update moniker being
|
||||
used
|
||||
|
||||
2001-07-31 Chema Celorio <chema@celorio.com>
|
||||
|
||||
* Makefile.am (cappletname): add DISTDIR to install-data-local
|
||||
|
|
|
@ -478,7 +478,7 @@ capplet_control_launch (const gchar *capplet_name, gchar *window_title)
|
|||
|
||||
tmp = g_strdup (capplet_name);
|
||||
if ((tmp1 = strstr (tmp, "-capplet")) != NULL) *tmp1 = '\0';
|
||||
moniker = g_strconcat ("archiver:", tmp, NULL);
|
||||
moniker = g_strconcat ("archive:user-archive#archiverdb:", tmp, NULL);
|
||||
while ((tmp1 = strchr (tmp, '-'))) *tmp1 = '_';
|
||||
|
||||
oaf_iid = g_strconcat ("OAFIID:Bonobo_Control_Capplet_", tmp, NULL);
|
||||
|
|
114
idl/ConfigArchiver.idl
Normal file
114
idl/ConfigArchiver.idl
Normal file
|
@ -0,0 +1,114 @@
|
|||
/* -*- mode: idl; style: linux -*- */
|
||||
|
||||
/* Bonobo_ConfigArchiver.idl
|
||||
* Copyright (C) 2001 Ximian, Inc.
|
||||
*
|
||||
* Written by Bradford Hovinen <hovinen@ximian.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2, 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 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.
|
||||
*/
|
||||
|
||||
#ifndef __CONFIGARCHIVER_IDL
|
||||
#define __CONFIGARCHIVER_IDL
|
||||
|
||||
%{
|
||||
#pragma include_defs bonobo/Bonobo.h
|
||||
%}
|
||||
#pragma inhibit push
|
||||
|
||||
#include <Bonobo_Unknown.idl>
|
||||
|
||||
#pragma inhibit pop
|
||||
|
||||
module ConfigArchiver {
|
||||
typedef unsigned long long Time;
|
||||
typedef sequence<string> StringSeq;
|
||||
|
||||
enum ContainmentType {
|
||||
CONTAIN_NONE, CONTAIN_PARTIAL, CONTAIN_FULL
|
||||
};
|
||||
|
||||
enum StoreType {
|
||||
STORE_DEFAULT, STORE_FULL, STORE_COMPARE_PARENT, STORE_MASK_PREVIOUS
|
||||
};
|
||||
|
||||
interface BackendList : Bonobo::Unknown {
|
||||
readonly attribute StringSeq backends;
|
||||
|
||||
boolean contains (in string backendId);
|
||||
|
||||
void add (in string backendId);
|
||||
void remove (in string backendId);
|
||||
|
||||
void save ();
|
||||
};
|
||||
|
||||
interface Location : Bonobo::Unknown {
|
||||
readonly attribute Location parent;
|
||||
readonly attribute string path;
|
||||
readonly attribute StringSeq backendList;
|
||||
|
||||
attribute string label;
|
||||
attribute string id;
|
||||
|
||||
string getStorageFilename (in string backendId,
|
||||
in boolean isDefaultData);
|
||||
|
||||
string getRollbackFilename (in Time time,
|
||||
in long steps,
|
||||
in string backendId,
|
||||
in boolean parentChain);
|
||||
|
||||
void rollbackBackends (in Time time,
|
||||
in long steps,
|
||||
in StringSeq backendId,
|
||||
in boolean parentChain);
|
||||
|
||||
Time getModificationTime (in string backendId);
|
||||
|
||||
ContainmentType contains (in string backendId);
|
||||
long addBackend (in string backendId,
|
||||
in ContainmentType type);
|
||||
void removeBackend (in string backendId);
|
||||
|
||||
boolean doesBackendChange (in Location location,
|
||||
in string backendId);
|
||||
|
||||
void garbageCollect ();
|
||||
|
||||
void delete ();
|
||||
};
|
||||
|
||||
typedef sequence<Location> LocationSeq;
|
||||
|
||||
interface Archive : Bonobo::Unknown {
|
||||
readonly attribute string prefix;
|
||||
readonly attribute boolean isGlobal;
|
||||
readonly attribute BackendList backendList;
|
||||
|
||||
attribute Location currentLocation;
|
||||
attribute string currentLocationId;
|
||||
|
||||
Location getLocation (in string locid);
|
||||
Location createLocation (in string locid,
|
||||
in string label,
|
||||
in Location parent);
|
||||
|
||||
LocationSeq getChildLocations (in Location parent);
|
||||
};
|
||||
};
|
||||
|
||||
#endif /* ! __CONFIGARCHIVER_IDL */
|
6
idl/Makefile.am
Normal file
6
idl/Makefile.am
Normal file
|
@ -0,0 +1,6 @@
|
|||
idldir = $(datadir)/idl
|
||||
|
||||
idl_DATA = ConfigArchiver.idl
|
||||
|
||||
EXTRA_DIST = $(idl_DATA)
|
||||
|
|
@ -1,5 +1,5 @@
|
|||
archiver/location.c
|
||||
archiver/main.c
|
||||
archiver/config-archiver.c
|
||||
capplets/background/applier.c
|
||||
capplets/background/background.desktop.in.in
|
||||
capplets/background/background-properties.glade
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue