ldb_rename()
Stefan (metze) Metzmacher
metze at samba.org
Mon Oct 18 19:55:15 GMT 2004
Hi tridge,
here's a preview patch for implmenting ldb_rename()
it's not complete currently, I need to test the semantics of
LDB_RENAME_FLG_DELETE_OLDRDN in ldap.
Can you look at the ltdb code and tell me if this looks ok or not?
--
metze
Stefan Metzmacher <metze at samba.org> www.samba.org
-------------- next part --------------
Index: lib/ldb/tools/ldbrename.c
===================================================================
--- lib/ldb/tools/ldbrename.c (revision 0)
+++ lib/ldb/tools/ldbrename.c (revision 0)
@@ -0,0 +1,109 @@
+/*
+ ldb database library
+
+ Copyright (C) Andrew Tridgell 2004
+ Copyright (C) Stefan Metzmacher 2004
+
+ ** NOTE! The following LGPL license applies to the ldb
+ ** library. This does NOT imply that all of Samba is released
+ ** under the LGPL
+
+ This library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2 of the License, or (at your option) any later version.
+
+ This library 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
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with this library; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+/*
+ * Name: ldb
+ *
+ * Component: ldbrename
+ *
+ * Description: utility to rename records - modelled on ldapmodrdn
+ *
+ * Author: Andrew Tridgell
+ * Author: Stefan Metzmacher
+ */
+
+#include "includes.h"
+
+static void usage(void)
+{
+ printf("Usage: ldbrename [<options>] <olddn> <newdn>\n");
+ printf("Options:\n");
+ printf(" -r remove old RDN\n");
+ printf(" -H ldb_url choose the database (or $LDB_URL)\n");
+ printf("\n");
+ printf("Renames records in a ldb\n\n");
+ exit(1);
+}
+
+
+ int main(int argc, char * const argv[])
+{
+ struct ldb_context *ldb;
+ const char *ldb_url;
+ int opt, ret;
+ int flags = 0;
+
+ ldb_url = getenv("LDB_URL");
+
+ while ((opt = getopt(argc, argv, "hH:r")) != EOF) {
+ switch (opt) {
+ case 'H':
+ ldb_url = optarg;
+ break;
+
+ case 'r':
+ flags |=LDB_RENAME_FLG_DELETE_OLDRDN;
+ break;
+
+ case 'h':
+ default:
+ usage();
+ break;
+ }
+ }
+
+ if (!ldb_url) {
+ fprintf(stderr, "You must specify a ldb URL\n\n");
+ usage();
+ }
+
+ argc -= optind;
+ argv += optind;
+
+ ldb = ldb_connect(ldb_url, 0, NULL);
+
+ if (!ldb) {
+ perror("ldb_connect");
+ exit(1);
+ }
+
+ ldb_set_debug_stderr(ldb);
+
+ if (argc < 2) {
+ usage();
+ }
+
+ ret = ldb_rename(ldb, argv[0], argv[1], flags);
+ if (ret == 0) {
+ printf("Renamed 1 record\n");
+ } else {
+ printf("rename of '%s' to '%s' rmolddn:%d failed - %s\n",
+ argv[0], argv[1], flags, ldb_errstring(ldb));
+ }
+
+ ldb_close(ldb);
+
+ return 0;
+}
Index: lib/ldb/ldb_ldap/ldb_ldap.c
===================================================================
--- lib/ldb/ldb_ldap/ldb_ldap.c (revision 3047)
+++ lib/ldb/ldb_ldap/ldb_ldap.c (working copy)
@@ -92,6 +92,33 @@
}
/*
+ rename a record
+ flags could be LDB_RENAME_FLG_DELETE_OLDRDN
+*/
+static int lldb_rename(struct ldb_context *ldb, const char *olddn, const char *newdn, unsigned int flags)
+{
+ struct lldb_private *lldb = ldb->private_data;
+ int ret = 0;
+ int deleteoldrdn = 0;
+
+ /* ignore ltdb specials */
+ if (olddn[0] == '@' ||newdn[0] == '@') {
+ return 0;
+ }
+
+ if (flags & LDB_RENAME_FLG_DELETE_OLDRDN) {
+ deleteoldrdn = 1;
+ }
+
+ lldb->last_rc = ldap_modrdn2_s(lldb->ldap, olddn, newdn, deleteoldrdn);
+ if (lldb->last_rc != LDAP_SUCCESS) {
+ ret = -1;
+ }
+
+ return ret;
+}
+
+/*
delete a record
*/
static int lldb_delete(struct ldb_context *ldb, const char *dn)
@@ -465,6 +492,7 @@
lldb_add,
lldb_modify,
lldb_delete,
+ lldb_rename,
lldb_errstring
};
Index: lib/ldb/include/ldb.h
===================================================================
--- lib/ldb/include/ldb.h (revision 3047)
+++ lib/ldb/include/ldb.h (working copy)
@@ -2,6 +2,7 @@
ldb database library
Copyright (C) Andrew Tridgell 2004
+ Copyright (C) Stefan Metzmacher 2004
** NOTE! The following LGPL license applies to the ldb
** library. This does NOT imply that all of Samba is released
@@ -30,6 +31,7 @@
* Description: defines for base ldb API
*
* Author: Andrew Tridgell
+ * Author: Stefan Metzmacher
*/
#ifndef _LDB_H_
@@ -131,6 +133,7 @@
int (*add_record)(struct ldb_context *, const struct ldb_message *);
int (*modify_record)(struct ldb_context *, const struct ldb_message *);
int (*delete_record)(struct ldb_context *, const char *);
+ int (*rename_record)(struct ldb_context *, const char *olddn, const char *newdn, unsigned int flags);
const char * (*errstring)(struct ldb_context *);
/* this is called when the alloc ops changes to ensure we
@@ -235,6 +238,13 @@
const struct ldb_message *message);
/*
+ rename a record in the database
+*/
+#define LDB_RENAME_FLG_DELETE_OLDRDN (1<<0)
+int ldb_rename(struct ldb_context *ldb,
+ const char *olddn, const char *newdn, unsigned int flags);
+
+/*
delete a record from the database
*/
int ldb_delete(struct ldb_context *ldb, const char *dn);
Index: lib/ldb/config.m4
===================================================================
--- lib/ldb/config.m4 (revision 3047)
+++ lib/ldb/config.m4 (working copy)
@@ -23,3 +23,5 @@
SMB_BINARY_MK(ldbsearch,lib/ldb/config.mk)
SMB_BINARY_MK(ldbedit,lib/ldb/config.mk)
+
+SMB_BINARY_MK(ldbrename,lib/ldb/config.mk)
Index: lib/ldb/common/ldb.c
===================================================================
--- lib/ldb/common/ldb.c (revision 3047)
+++ lib/ldb/common/ldb.c (working copy)
@@ -140,6 +140,17 @@
}
/*
+ rename a record in the database
+*/
+int ldb_rename(struct ldb_context *ldb, const char *olddn, const char *newdn, unsigned int flags)
+{
+ int ret;
+ ret = ldb->ops->rename_record(ldb, olddn, newdn, flags);
+ ldb_debug(ldb, LDB_DEBUG_TRACE, "ldb_rename(%s,%s,%d) -> %d\n", olddn, newdn, flags, ret);
+ return ret;
+}
+
+/*
return extended error information
*/
const char *ldb_errstring(struct ldb_context *ldb)
Index: lib/ldb/ldb_tdb/ldb_tdb.c
===================================================================
--- lib/ldb/ldb_tdb/ldb_tdb.c (revision 3047)
+++ lib/ldb/ldb_tdb/ldb_tdb.c (working copy)
@@ -582,6 +582,69 @@
}
/*
+ rename a record
+*/
+static int ltdb_rename(struct ldb_context *ldb, const char *olddn, const char *newdn, unsigned int flags)
+{
+ struct ltdb_private *ltdb = ldb->private_data;
+ int ret;
+ struct ldb_message msg;
+
+ /* TODO: handle flags correct
+ * the LDB_RENAME_FLG_DELETE_OLDRDN should be checked
+ */
+
+ ltdb->last_err_string = NULL;
+
+ if (ltdb_lock(ldb) != 0) {
+ return -1;
+ }
+
+ if (ltdb_cache_load(ldb) != 0) {
+ ltdb_unlock(ldb);
+ return -1;
+ }
+
+ /* in case any attribute of the message was indexed, we need
+ to fetch the old record */
+ ret = ltdb_search_dn1(ldb, olddn, &msg);
+ if (ret != 1) {
+ /* not finding the old record is an error */
+ goto failed;
+ }
+
+ msg.dn = discard_const_p(char, newdn);
+
+ ret = ltdb_store(ldb, &msg, TDB_INSERT);
+ if (ret == -1) {
+ ltdb_search_dn1_free(ldb, &msg);
+ goto failed;
+ }
+
+ ret = ltdb_delete_noindex(ldb, olddn);
+ if (ret == -1) {
+ ltdb_delete_noindex(ldb, newdn);
+ ltdb_search_dn1_free(ldb, &msg);
+ goto failed;
+ }
+
+ /* remove any indexed attributes of the old dn */
+ msg.dn = discard_const_p(char, olddn);
+ ret = ltdb_index_del(ldb, &msg);
+
+ ltdb_search_dn1_free(ldb, &msg);
+
+ ltdb_modified(ldb, newdn);
+
+ ltdb_unlock(ldb);
+
+ return ret;
+failed:
+ ltdb_unlock(ldb);
+ return -1;
+}
+
+/*
close database
*/
static int ltdb_close(struct ldb_context *ldb)
@@ -621,6 +684,7 @@
ltdb_add,
ltdb_modify,
ltdb_delete,
+ ltdb_rename,
ltdb_errstring,
ltdb_cache_free
};
Index: lib/ldb/config.mk
===================================================================
--- lib/ldb/config.mk (revision 3047)
+++ lib/ldb/config.mk (working copy)
@@ -102,3 +102,13 @@
LIBBASIC CONFIG LIBCMDLINE LIBLDB
# End BINARY ldbedit
################################################
+
+################################################
+# Start BINARY ldbrename
+[BINARY::ldbrename]
+OBJ_FILES= \
+ lib/ldb/tools/ldbrename.o
+REQUIRED_SUBSYSTEMS = \
+ LIBBASIC CONFIG LIBCMDLINE LIBLDB
+# End BINARY ldbrename
+################################################
More information about the samba-technical
mailing list