char *wanted;
/* Define the plan. */
- plan(32);
+ plan(47);
/* Set up a temporary directory and queue relative to it. */
tmpdir = test_tmpdir();
bail_krb5(ctx, code, "cannot parse principal test@EXAMPLE.COM");
sync_queue_block("queue", "test", "password");
code = sync_chpass(data, ctx, princ, "foobar");
- is_int(0, code, "pwupdate_precommit_password succeeds");
+ is_int(0, code, "sync_chpass succeeds");
ok(access("queue/.lock", F_OK) == 0, "...lock file now exists");
sync_queue_check_password("queue", "test", "foobar");
sync_queue_unblock("queue", "test", "password");
sync_queue_check_enable("queue", "test", false);
sync_queue_unblock("queue", "test", "enable");
+ /* Queue a password change for a root instance. */
+ krb5_free_principal(ctx, princ);
+ code = krb5_parse_name(ctx, "test/root@EXAMPLE.COM", &princ);
+ if (code != 0)
+ bail_krb5(ctx, code, "cannot parse principal test/root@EXAMPLE.COM");
+ sync_queue_block("queue", "test/root", "password");
+ code = sync_chpass(data, ctx, princ, "foobar");
+ is_int(0, code, "sync_chpass of root instance succeeds");
+ sync_queue_check_password("queue", "test/root", "foobar");
+ sync_queue_unblock("queue", "test/root", "password");
+
+ /* Queue an account disable for an ipass instance. */
+ krb5_free_principal(ctx, princ);
+ code = krb5_parse_name(ctx, "test/ipass@EXAMPLE.COM", &princ);
+ if (code != 0)
+ bail_krb5(ctx, code, "cannot parse principal test/ipass@EXAMPLE.COM");
+ sync_queue_block("queue", "test/ipass", "enable");
+ code = sync_status(data, ctx, princ, true);
+ is_int(0, code, "sync_status of root instance succeeds");
+ sync_queue_check_enable("queue", "test/ipass", true);
+ sync_queue_unblock("queue", "test/ipass", "enable");
+
+ /*
+ * Try queuing a change for an admin instance, which should do nothing,
+ * successfully. We'll test there's no queued changes by deleting the
+ * queue file.
+ */
+ krb5_free_principal(ctx, princ);
+ code = krb5_parse_name(ctx, "test/admin@EXAMPLE.COM", &princ);
+ if (code != 0)
+ bail_krb5(ctx, code, "cannot parse principal test/admin@EXAMPLE.COM");
+ code = sync_chpass(data, ctx, princ, "foobar");
+ is_int(0, code, "sync_chpass of admin instance succeeds");
+ code = sync_status(data, ctx, princ, true);
+ is_int(0, code, "sync_status enable of admin instance succeeds");
+
/* Unwind the queue and be sure all the right files exist. */
ok(unlink("queue/.lock") == 0, "Lock file still exists");
ok(rmdir("queue") == 0, "No other files in queue directory");
/* Check failure when there's no queue directory. */
+ krb5_free_principal(ctx, princ);
+ code = krb5_parse_name(ctx, "test/root@EXAMPLE.COM", &princ);
+ if (code != 0)
+ bail_krb5(ctx, code, "cannot parse principal test/root@EXAMPLE.COM");
basprintf(&wanted, "cannot open lock file queue/.lock: %s",
strerror(ENOENT));
code = sync_chpass(data, ctx, princ, "foobar");
#include <tests/tap/sync.h>
+/*
+ * Format the user for queue file naming. This just replaces all slashes with
+ * periods and returns the new user as a newly-allocated string.
+ */
+static char *
+munge_user(const char *user)
+{
+ char *munged_user, *p;
+
+ munged_user = bstrdup(user);
+ for (p = munged_user; *p != '\0'; p++)
+ if (*p == '/')
+ *p = '.';
+ return munged_user;
+}
+
+
/*
* Block processing by creating a dummy queue file. Takes the queue
* directory, the username (as used for queuing), and the operation to block.
sync_queue_block(const char *queue, const char *user, const char *op)
{
int fd;
- char *file;
+ char *file, *munged_user;
- basprintf(&file, "%s/%s-ad-%s-19700101T000000Z", queue, user, op);
+ munged_user = munge_user(user);
+ basprintf(&file, "%s/%s-ad-%s-19700101T000000Z", queue, munged_user, op);
+ free(munged_user);
fd = open(file, O_CREAT | O_WRONLY, 0666);
if (fd < 0)
sysbail("cannot create blocking queue file %s", file);
void
sync_queue_unblock(const char *queue, const char *user, const char *op)
{
- char *file;
+ char *file, *munged_user;
- basprintf(&file, "%s/%s-ad-%s-19700101T000000Z", queue, user, op);
+ munged_user = munge_user(user);
+ basprintf(&file, "%s/%s-ad-%s-19700101T000000Z", queue, munged_user, op);
+ free(munged_user);
if (unlink(file) < 0)
sysbail("cannot delete blocking queue file %s", file);
free(file);
queue_check(const char *queue, const char *user, const char *op,
const char *password)
{
- char *path, *wanted;
+ char *path, *wanted, *munged_user;
const char *path_op;
time_t now, timestamp;
struct tm *date;
path = NULL;
now = time(NULL);
path_op = (strcmp("disable", op) == 0) ? "enable" : op;
+ munged_user = munge_user(user);
for (timestamp = now - 1; timestamp <= now; timestamp++) {
date = gmtime(×tamp);
basprintf(&path, "%s/%s-ad-%s-%04d%02d%02dT%02d%02d%02dZ-00", queue,
- user, path_op, date->tm_year + 1900, date->tm_mon + 1,
+ munged_user, path_op, date->tm_year + 1900, date->tm_mon + 1,
date->tm_mday, date->tm_hour, date->tm_min, date->tm_sec);
if (access(path, F_OK) == 0)
break;
free(path);
path = NULL;
}
+ free(munged_user);
/* Check that we found a queued change. */
ok(path != NULL, "%s for %s was queued", op, user);