Commit b310371c authored by Marius Vollmer's avatar Marius Vollmer
Browse files

Library: Support for groups.

parent d67ad309
......@@ -13,6 +13,7 @@ HFILE_GLOB=$(top_srcdir)/src/libaccountsservice/*.h
IGNORE_HFILES= \
accounts-generated.h \
accounts-user-generated.h \
accounts-group-generated.h \
ck-manager-generated.h \
ck-seat-generated.h \
ck-session-generated.h \
......
......@@ -12,6 +12,7 @@
<chapter>
<title>libaccountsservice</title>
<xi:include href="xml/act-user.xml"/>
<xi:include href="xml/act-group.xml"/>
<xi:include href="xml/act-user-manager.xml"/>
</chapter>
......
......@@ -15,7 +15,9 @@ act_user_get_locked
act_user_get_login_frequency
act_user_get_login_history
act_user_get_login_time
act_user_get_manager
act_user_get_num_sessions
act_user_get_num_sessions_anywhere
act_user_get_object_path
act_user_get_password_hint
act_user_get_password_mode
......@@ -25,10 +27,13 @@ act_user_get_shell
act_user_get_uid
act_user_get_user_name
act_user_get_x_session
act_user_get_cached_groups
act_user_is_loaded
act_user_is_local_account
act_user_is_logged_in
act_user_is_logged_in_anywhere
act_user_is_system_account
act_user_is_nonexistent
act_user_set_account_type
act_user_set_automatic_login
act_user_set_email
......@@ -41,6 +46,9 @@ act_user_set_password_mode
act_user_set_real_name
act_user_set_user_name
act_user_set_x_session
act_user_find_groups
act_user_find_groups_async
act_user_find_groups_finish
<SUBSECTION Standard>
ActUserClass
ACT_IS_USER
......@@ -49,6 +57,27 @@ ACT_USER
act_user_get_type
</SECTION>
<SECTION>
<FILE>act-group</FILE>
ActGroup
act_group_get_gid
act_group_get_group_name
act_group_get_manager
act_group_get_object_path
act_group_get_users
act_group_is_loaded
act_group_is_nonexistent
act_group_set_group_name
act_group_add_user
act_group_remove_user
<SUBSECTION Standard>
ACT_GROUP
ACT_IS_GROUP
ACT_TYPE_GROUP
ActGroupClass
act_group_get_type
</SECTION>
<SECTION>
<FILE>act-user-manager</FILE>
ACT_USER_MANAGER_ERROR
......@@ -72,6 +101,15 @@ act_user_manager_goto_login_session
act_user_manager_list_users
act_user_manager_no_service
act_user_manager_uncache_user
act_user_manager_create_group
act_user_manager_create_group_async
act_user_manager_create_group_finish
act_user_manager_delete_group
act_user_manager_delete_group_async
act_user_manager_delete_group_finish
act_user_manager_get_group
act_user_manager_get_group_by_id
act_user_manager_list_groups
<SUBSECTION Standard>
ActUserManagerClass
ACT_IS_USER_MANAGER
......@@ -108,4 +146,4 @@ act_user_manager_error_quark
<SECTION>
<FILE>ConsoleKitManager</FILE>
</SECTION>
\ No newline at end of file
</SECTION>
act_user_get_type
act_group_get_type
act_user_manager_get_type
......@@ -61,7 +61,9 @@ CLEANFILES += $(BUILT_SOURCES)
libaccountsservicedir = $(includedir)/accountsservice-1.0/act
libaccountsservice_headers = \
act-types.h \
act-user.h \
act-group.h \
act-user-manager.h \
act-user-enum-types.h \
$(END_OF_LIST)
......@@ -80,7 +82,7 @@ libaccountsservice_la_LDFLAGS = \
$(END_OF_LIST)
libaccountsservice_la_LIBADD = \
../libaccounts-generated.la \
../libaccounts-generated.la \
$(LIBACCOUNTSSERVICE_LIBS) \
-lcrypt \
$(END_OF_LIST)
......@@ -88,12 +90,15 @@ libaccountsservice_la_LIBADD = \
libaccountsservice_la_sources = \
$(libaccountsservice_headers) \
act-user.c \
act-group.c \
act-user-manager.c \
$(END_OF_LIST)
libaccountsservice_la_SOURCES = \
$(libaccountsservice_la_sources) \
act-user-manager-private.h \
act-user-private.h \
act-group-private.h \
$(BUILT_SOURCES) \
$(END_OF_LIST)
......
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 8 -*-
*
* Copyright (C) 2004-2005 James M. Cape <jcape@ignore-your.tv>.
*
* 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 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU 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
*/
/*
* Private interfaces to the ActGroup object
*/
#ifndef __ACT_GROUP_PRIVATE_H_
#define __ACT_GROUP_PRIVATE_H_
#include <pwd.h>
#include "act-user-manager.h"
#include "act-group.h"
G_BEGIN_DECLS
void _act_group_update_from_object_path (ActUserManager *manager,
ActGroup *group,
const char *object_path);
void _act_group_update_as_nonexistent (ActGroup *group);
void _act_group_load_from_group (ActGroup *group,
ActGroup *group_to_copy);
G_END_DECLS
#endif /* !__ACT_GROUP_PRIVATE_H_ */
This diff is collapsed.
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 8 -*-
*
* Copyright (C) 2013 Red Hat
*
* 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 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU 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
*/
/*
* Facade object for group data, owned by ActUserManager
*/
#ifndef __ACT_GROUP_H__
#define __ACT_GROUP_H__
#include <sys/types.h>
#include <glib.h>
#include <glib-object.h>
#include "act-types.h"
G_BEGIN_DECLS
#define ACT_TYPE_GROUP (act_group_get_type ())
#define ACT_GROUP(object) (G_TYPE_CHECK_INSTANCE_CAST ((object), ACT_TYPE_GROUP, ActGroup))
#define ACT_IS_GROUP(object) (G_TYPE_CHECK_INSTANCE_TYPE ((object), ACT_TYPE_GROUP))
typedef struct _ActGroupClass ActGroupClass;
GType act_group_get_type (void) G_GNUC_CONST;
ActUserManager *act_group_get_manager (ActGroup *group);
const char *act_group_get_object_path (ActGroup *group);
gboolean act_group_is_loaded (ActGroup *group);
gboolean act_group_is_nonexistent (ActGroup *group);
gid_t act_group_get_gid (ActGroup *group);
const char *act_group_get_group_name (ActGroup *group);
ActUser **act_group_get_users (ActGroup *group);
void act_group_set_group_name (ActGroup *group,
const gchar *new_group_name);
void act_group_add_user (ActGroup *group,
ActUser *user);
void act_group_remove_user (ActGroup *group,
ActUser *user);
G_END_DECLS
#endif /* __ACT_GROUP_H__ */
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 8 -*-
*
* Copyright (C) 2013 Red Hat, Inc.
*
* 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 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU 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 __ACT_TYPES_H__
#define __ACT_TYPES_H__
typedef struct _ActUser ActUser;
typedef struct _ActGroup ActGroup;
typedef struct _ActUserManager ActUserManager;
#endif /* __ACT_TYPES_H__ */
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 8 -*-
*
* Copyright (C) 2013 Red Hat
*
* 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 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU 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
*/
/*
* Private interfaces to the ActUserManager object
*/
#ifndef __ACT_USER_MANAGER_PRIVATE_H_
#define __ACT_USER_MANAGER_PRIVATE_H_
#include <pwd.h>
#include "act-user-manager.h"
G_BEGIN_DECLS
ActUser *_act_user_manager_get_user (ActUserManager *manager,
const char *object_path);
ActGroup *_act_user_manager_get_group (ActUserManager *manager,
const char *group_path);
G_END_DECLS
#endif /* !__ACT_GROUP_PRIVATE_H_ */
This diff is collapsed.
......@@ -24,7 +24,9 @@
#include <glib-object.h>
#include <gio/gio.h>
#include "act-types.h"
#include "act-user.h"
#include "act-group.h"
G_BEGIN_DECLS
......@@ -58,7 +60,13 @@ struct _ActUserManagerClass
void (* user_is_logged_in_changed) (ActUserManager *user_manager,
ActUser *user);
void (* user_changed) (ActUserManager *user_manager,
ActUser *user);
ActGroup *group);
void (* group_added) (ActUserManager *user_manager,
ActGroup *group);
void (* group_removed) (ActUserManager *user_manager,
ActGroup *group);
void (* group_changed) (ActUserManager *user_manager,
ActGroup *group);
};
typedef enum ActUserManagerError
......@@ -67,7 +75,9 @@ typedef enum ActUserManagerError
ACT_USER_MANAGER_ERROR_USER_EXISTS,
ACT_USER_MANAGER_ERROR_USER_DOES_NOT_EXIST,
ACT_USER_MANAGER_ERROR_PERMISSION_DENIED,
ACT_USER_MANAGER_ERROR_NOT_SUPPORTED
ACT_USER_MANAGER_ERROR_NOT_SUPPORTED,
ACT_USER_MANAGER_ERROR_GROUP_EXISTS,
ACT_USER_MANAGER_ERROR_GROUP_DOES_NOT_EXIST
} ActUserManagerError;
#define ACT_USER_MANAGER_ERROR act_user_manager_error_quark ()
......@@ -84,6 +94,12 @@ ActUser * act_user_manager_get_user (ActUserManager *mana
ActUser * act_user_manager_get_user_by_id (ActUserManager *manager,
uid_t id);
GSList * act_user_manager_list_groups (ActUserManager *manager);
ActGroup * act_user_manager_get_group (ActUserManager *manager,
const char *groupname);
ActGroup * act_user_manager_get_group_by_id (ActUserManager *manager,
gid_t id);
gboolean act_user_manager_activate_user_session (ActUserManager *manager,
ActUser *user);
......@@ -137,6 +153,30 @@ gboolean act_user_manager_delete_user_finish (ActUserManager *
GAsyncResult *result,
GError **error);
ActGroup* act_user_manager_create_group (ActUserManager *manager,
const char *groupname,
GError **error);
void act_user_manager_create_group_async (ActUserManager *manager,
const gchar *groupname,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data);
ActGroup* act_user_manager_create_group_finish (ActUserManager *manager,
GAsyncResult *result,
GError **error);
gboolean act_user_manager_delete_group (ActUserManager *manager,
ActGroup *group,
GError **error);
void act_user_manager_delete_group_async (ActUserManager *manager,
ActGroup *group,
GCancellable *cancellable,
GAsyncReadyCallback callback,
gpointer user_data);
gboolean act_user_manager_delete_group_finish (ActUserManager *manager,
GAsyncResult *result,
GError **error);
G_END_DECLS
#endif /* __ACT_USER_MANAGER_H__ */
......@@ -26,12 +26,14 @@
#include <pwd.h>
#include "act-user-manager.h"
#include "act-user.h"
G_BEGIN_DECLS
void _act_user_update_from_object_path (ActUser *user,
const char *object_path);
void _act_user_update_from_object_path (ActUserManager *manager,
ActUser *user,
const char *object_path);
void _act_user_update_as_nonexistent (ActUser *user);
void _act_user_update_login_frequency (ActUser *user,
int login_frequency);
......
......@@ -31,6 +31,7 @@
#include <gio/gio.h>
#include "act-user-private.h"
#include "act-user-manager-private.h"
#include "accounts-user-generated.h"
/**
......@@ -106,6 +107,7 @@ enum {
struct _ActUser {
GObject parent;
ActUserManager *manager;
GDBusConnection *connection;
AccountsUser *accounts_proxy;
GDBusProxy *object_proxy;
......@@ -132,6 +134,8 @@ struct _ActUser {
ActUserAccountType account_type;
ActUserPasswordMode password_mode;
ActGroup **cached_groups;
guint uid_set : 1;
guint is_loaded : 1;
......@@ -564,6 +568,17 @@ act_user_init (ActUser *user)
}
}
static void
free_group_array (ActGroup **a)
{
int i;
if (a) {
for (i = 0; a[i]; i++)
g_object_unref (a[i]);
g_free (a);
}
}
static void
act_user_finalize (GObject *object)
{
......@@ -600,6 +615,8 @@ act_user_finalize (GObject *object)
g_object_unref (user->connection);
}
free_group_array (user->cached_groups);
if (G_OBJECT_CLASS (act_user_parent_class)->finalize)
(*G_OBJECT_CLASS (act_user_parent_class)->finalize) (object);
}
......@@ -836,6 +853,23 @@ act_user_get_login_history (ActUser *user) {
return user->login_history;
}
/**
* act_user_get_cached_groups:
* @user: a #ActUser
*
* Returns the cached groups for @user.
*
* Returns: (transfer none): A %NULL-terminated array of pointers to #ActGroup objects.
*
* Since: 0.6.36
*/
ActGroup **
act_user_get_cached_groups (ActUser *user) {
g_return_val_if_fail (ACT_IS_USER (user), NULL);
return user->cached_groups;
}
/**
* act_user_collate:
* @user1: a user
......@@ -1069,7 +1103,7 @@ act_user_get_x_session (ActUser *user)
/**
* act_user_get_object_path:
* @user: a #ActUser
* @user: a user
*
* Returns the user accounts service object path of @user,
* or %NULL if @user doesn't have an object path associated
......@@ -1085,6 +1119,20 @@ act_user_get_object_path (ActUser *user)
return user->object_path;
}
/**
* act_user_get_manager:
* @user: a #ActUser
*
* Returns the #ActUserManager that this #ActUser object belongs to.
*
* Returns: (transfer none): the #ActUserManager
*/
ActUserManager *
act_user_get_manager (ActUser *user)
{
return user->manager;
}
/**
* act_user_get_primary_session_id:
* @user: a #ActUser
......@@ -1288,6 +1336,41 @@ collect_props (const gchar *key,
user->x_session = g_strdup (new_x_session);
g_object_notify (G_OBJECT (user), "x-session");
}
} else if (strcmp (key, "CachedGroups") == 0) {
gboolean changed;
GVariantIter iter;
int i;
const gchar *group_path;
if (user->cached_groups == NULL)
changed = TRUE;
else {
changed = FALSE;
i = 0;
g_variant_iter_init (&iter, value);
while (user->cached_groups[i] && g_variant_iter_next (&iter, "&o", &group_path)) {
if (g_strcmp0 (act_group_get_object_path (user->cached_groups[i]), group_path) != 0) {
changed = TRUE;
break;
}
i++;
}
if (user->cached_groups[i] != NULL || i != g_variant_n_children (value))
changed = TRUE;
}
if (changed) {
free_group_array (user->cached_groups);
user->cached_groups = g_new0 (ActGroup*, g_variant_n_children (value)+1);
i = 0;
g_variant_iter_init (&iter, value);
while (g_variant_iter_next (&iter, "&o", &group_path)) {
user->cached_groups[i] = g_object_ref(_act_user_manager_get_group (user->manager,
group_path));
i++;
}
// g_object_notify (G_OBJECT (user), "cached-groups");
}
} else {
handled = FALSE;
}
......@@ -1405,15 +1488,18 @@ _act_user_update_as_nonexistent (ActUser *user)
* the object path in @object_path.
**/
void
_act_user_update_from_object_path (ActUser *user,
const char *object_path)
_act_user_update_from_object_path (ActUserManager *manager,
ActUser *user,
const char *object_path)
{
GError *error = NULL;
g_return_if_fail (ACT_IS_USER_MANAGER (manager));
g_return_if_fail (ACT_IS_USER (user));
g_return_if_fail (object_path != NULL);
g_return_if_fail (user->object_path == NULL);
user->manager = manager;
user->object_path = g_strdup (object_path);
user->accounts_proxy = accounts_user_proxy_new_sync (user->connection,
......@@ -1965,3 +2051,152 @@ act_user_set_automatic_login (ActUser *user,
g_error_free (error);
}
}
static ActGroup **
convert_group_paths (ActUserManager *manager,
gchar **paths)
{
int i, n;
ActGroup **res;
if (paths == NULL)
return NULL;
n = g_strv_length (paths);
res = g_new0 (ActGroup*, n+1);
for (i = 0; i < n; i++)
res[i] = g_object_ref (_act_user_manager_get_group (manager, paths[i]));
return res;
}
/**
* act_user_find_groups:
* @user: an #ActUser object
* @indirect: %TRUE to also list groups with indirect membership
* @error: a #GError
*
* Finds the groups of a user. This operation might query remote
* databases and thus be slow.
*
* Returns: (transfer full): A %NULL-terminated array of pointers to
* #ActGroup objects. Free it by unreffing all #ActGroup objects and
* then calling #g_free on the array. Returns %NULL in case of error.
*/
ActGroup **
act_user_find_groups (ActUser *user,
gboolean indirect,
GError **error)
{
GError *local_error;