summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Makefile.am3
-rw-r--r--Makefile.in3
-rw-r--r--ldap/admin/src/scripts/DSMigration.pm.in10
-rw-r--r--ldap/admin/src/scripts/FileConn.pm389
-rw-r--r--ldap/admin/src/scripts/Resource.pm4
-rw-r--r--ldap/admin/src/scripts/Util.pm.in64
-rw-r--r--ldap/admin/src/scripts/setup-ds.pl.in4
-rw-r--r--ldap/admin/src/scripts/setup-ds.res.in6
8 files changed, 451 insertions, 32 deletions
diff --git a/Makefile.am b/Makefile.am
index ea116701..236041a3 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -200,7 +200,8 @@ perl_SCRIPTS = ldap/admin/src/scripts/SetupLog.pm \
ldap/admin/src/scripts/DSDialogs.pm \
ldap/admin/src/scripts/Setup.pm \
ldap/admin/src/scripts/Migration.pm \
- ldap/admin/src/scripts/DSMigration.pm
+ ldap/admin/src/scripts/DSMigration.pm \
+ ldap/admin/src/scripts/FileConn.pm
property_DATA = ldap/admin/src/scripts/setup-ds.res \
ldap/admin/src/scripts/migrate-ds.res
diff --git a/Makefile.in b/Makefile.in
index 6235d97b..abb30db3 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -1137,7 +1137,8 @@ perl_SCRIPTS = ldap/admin/src/scripts/SetupLog.pm \
ldap/admin/src/scripts/DSDialogs.pm \
ldap/admin/src/scripts/Setup.pm \
ldap/admin/src/scripts/Migration.pm \
- ldap/admin/src/scripts/DSMigration.pm
+ ldap/admin/src/scripts/DSMigration.pm \
+ ldap/admin/src/scripts/FileConn.pm
property_DATA = ldap/admin/src/scripts/setup-ds.res \
ldap/admin/src/scripts/migrate-ds.res
diff --git a/ldap/admin/src/scripts/DSMigration.pm.in b/ldap/admin/src/scripts/DSMigration.pm.in
index 86f0cb4d..0e037044 100644
--- a/ldap/admin/src/scripts/DSMigration.pm.in
+++ b/ldap/admin/src/scripts/DSMigration.pm.in
@@ -374,6 +374,7 @@ sub migrateDS {
my $mig = shift;
$pkgname = $mig->{pkgname}; # set globals
$oldsroot = $mig->{oldsroot}; # set globals
+ my @errs;
# for each instance
foreach my $inst (@{$mig->{instances}}) {
@@ -388,13 +389,18 @@ sub migrateDS {
# extract the information needed for ds_newinst.pl
my $configdir = "$oldsroot/$inst/config";
- my $inf = createInfFromConfig($configdir, $inst);
+ my $inf = createInfFromConfig($configdir, $inst, \@errs);
debug(2, "Using inffile $inf->{filename} created from $configdir\n");
+ if (@errs) {
+ $mig->msg(@errs);
+ return 0;
+ }
# create the new instance
- my ($rc, $output) = createDSInstance($inf);
+ my ($rc, $output) = createDSInstance($inf, \@errs);
unlink($inf->{filename});
if ($rc) {
+ $mig->msg(@errs);
$mig->msg($FATAL, 'error_creating_dsinstance', $rc, $output);
return 0;
} else {
diff --git a/ldap/admin/src/scripts/FileConn.pm b/ldap/admin/src/scripts/FileConn.pm
new file mode 100644
index 00000000..c777b156
--- /dev/null
+++ b/ldap/admin/src/scripts/FileConn.pm
@@ -0,0 +1,389 @@
+# BEGIN COPYRIGHT BLOCK
+# 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; version 2 of the License.
+#
+# 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.
+#
+# In addition, as a special exception, Red Hat, Inc. gives You the additional
+# right to link the code of this Program with code not covered under the GNU
+# General Public License ("Non-GPL Code") and to distribute linked combinations
+# including the two, subject to the limitations in this paragraph. Non-GPL Code
+# permitted under this exception must only link to the code of this Program
+# through those well defined interfaces identified in the file named EXCEPTION
+# found in the source code files (the "Approved Interfaces"). The files of
+# Non-GPL Code may instantiate templates or use macros or inline functions from
+# the Approved Interfaces without causing the resulting work to be covered by
+# the GNU General Public License. Only Red Hat, Inc. may make changes or
+# additions to the list of Approved Interfaces. You must obey the GNU General
+# Public License in all respects for all of the Program code and other code used
+# in conjunction with the Program except the Non-GPL Code covered by this
+# exception. If you modify this file, you may extend this exception to your
+# version of the file, but you are not obligated to do so. If you do not wish to
+# provide this exception without modification, you must delete this exception
+# statement from your version and license this file solely under the GPL without
+# exception.
+#
+#
+# Copyright (C) 2007 Red Hat, Inc.
+# All rights reserved.
+# END COPYRIGHT BLOCK
+#
+# FileConn is a subclass of Mozilla::LDAP::Conn. This class does
+# not use LDAP. Instead, it operates on a given LDAP file, allowing
+# you to search, add, modify, and delete entries in the file.
+#
+package FileConn;
+
+use Mozilla::LDAP::Conn;
+use Mozilla::LDAP::API qw(:constant ldap_explode_dn ldap_err2string); # Direct access to C API
+use Mozilla::LDAP::Utils qw(normalizeDN);
+use Mozilla::LDAP::LDIF;
+
+require Exporter;
+@ISA = qw(Exporter Mozilla::LDAP::Conn);
+@EXPORT = qw();
+@EXPORT_OK = qw();
+
+sub new {
+ my $class = shift;
+ my $filename = shift;
+ my $self = {};
+
+ $self = bless $self, $class;
+
+ $self->read($filename);
+
+ return $self;
+}
+
+sub getParentDN {
+ my $dn = shift;
+ my @rdns = ldap_explode_dn($dn, 0);
+ shift @rdns;
+ return join(',', @rdns);
+}
+
+sub read {
+ my $self = shift;
+ my $filename = shift;
+
+ if ($filename) {
+ $self->{filename} = $filename;
+ } else {
+ $filename = $self->{filename};
+ }
+
+ if (!$self->{filename}) {
+ return;
+ }
+
+ open( MYLDIF, "$filename" ) || die "Can't open $filename: $!";
+ my $in = new Mozilla::LDAP::LDIF(*MYLDIF);
+ while ($ent = readOneEntry $in) {
+ if (!$self->add($ent)) {
+ die "Error: could not add entry ", $ent->getDN(), ":", $self->getErrorString();
+ }
+ }
+ close( MYLDIF );
+}
+
+# return all nodes below the given node
+sub iterate {
+ my $self = shift;
+ my $dn = shift;
+ my $scope = shift;
+ my $callback = shift;
+ my $context = shift;
+ my $suppress = shift;
+ my $ndn = normalizeDN($dn);
+ my $children = $self->{$ndn}->{children};
+ if (($scope != LDAP_SCOPE_ONELEVEL) && $self->{$ndn}->{data} && !$suppress) {
+ &{$callback}($self->{$ndn}->{data}, $context);
+ }
+
+ if ($scope == LDAP_SCOPE_BASE) {
+ return;
+ }
+
+ for my $node (@{$children}) {
+ &{$callback}($node->{data}, $context);
+ }
+ if ($scope == LDAP_SCOPE_SUBTREE) {
+ for my $node (@{$children}) {
+ $self->iterate($node->{data}->getDN(), $scope, $callback, $context, 1);
+ }
+ }
+}
+
+sub writecb {
+ my $entry = shift;
+ my $fh = shift;
+ if (! $entry->getDN()) { # rootDSE requires special hack around perldap bug
+ my $ary = $entry->getLDIFrecords();
+ shift @$ary; # remove "dn"
+ shift @$ary; # remove the empty dn value
+ print $fh "dn:\n";
+ print $fh (Mozilla::LDAP::LDIF::pack_LDIF (78, $ary), "\n");
+ } else {
+ Mozilla::LDAP::LDIF::put_LDIF($fh, 78, $entry);
+ }
+}
+
+sub write {
+ my $self = shift;
+ my $filename = shift;
+
+ if ($filename) {
+ $self->{filename} = $filename;
+ } else {
+ $filename = $self->{filename};
+ }
+
+ if (!$self->{filename}) {
+ return;
+ }
+
+ open( MYLDIF, ">$filename" ) || die "Can't write $filename: $!";
+ $self->iterate("", LDAP_SCOPE_SUBTREE, \&writecb, \*MYLDIF);
+ close( MYLDIF );
+}
+
+sub setErrorCode {
+ my $self = shift;
+ $self->{lastErrorCode} = shift;
+}
+
+sub getErrorCode {
+ my $self = shift;
+ return $self->{lastErrorCode};
+}
+
+sub getErrorString {
+ my $self = shift;
+ return ($self->{lastErrorCode} ? ldap_err2string($self->{lastErrorCode}) : LDAP_SUCCESS);
+}
+
+#############################################################################
+# Print the last error code...
+#
+sub printError
+{
+ my ($self, $str) = @_;
+
+ $str = "LDAP error:" unless defined($str);
+ print "$str ", $self->getErrorString(), "\n";
+}
+
+sub close {
+ my $self = shift;
+ $self->write();
+}
+
+sub printcb {
+ my $entry = shift;
+
+ print $entry->getDN(), "\n";
+}
+
+sub print {
+ my $self = shift;
+ my $dn = shift;
+ my $scope = shift;
+ $self->iterate($dn, $scope, \&printcb);
+}
+
+# for each entry, call the user provided filter callback
+# with the entry and the user provided filter context
+# if the filtercb returns true, add the entry to the
+# list of entries to return
+sub searchcb {
+ my $entry = shift;
+ my $context = shift;
+ my $self = $context->[0];
+ my $filtercb = $context->[1];
+ my $filtercontext = $context->[2];
+ if (&{$filtercb}($entry, $filtercontext)) {
+ push @{$self->{entries}}, $entry;
+ }
+}
+
+sub matchall {
+ return 1;
+}
+
+sub matchAttrVal {
+ my $entry = shift;
+ my $context = shift;
+ my $attr = $context->[0];
+ my $val = $context->[1];
+
+ if ($val eq "*") {
+ return $entry->exists($attr);
+ }
+ return $entry->hasValue($attr, $val, 1);
+}
+
+my $attrpat = '[-;.:\w]*[-;\w]';
+
+# given a string filter, figure out which subroutine to
+# use to match
+sub filterToMatchSub {
+ my $self = shift;
+ my ($basedn, $scope, $filter, $attrsonly, @rest) = @_;
+ my ($matchsub, $context);
+# do some filter processing
+ if (!$filter or ($filter eq "(objectclass=*)") or
+ ($filter eq "objectclass=*")) {
+ $matchsub = \&matchall;
+ } elsif ($filter =~ /^\(($attrpat)=(.+)\)$/o) {
+ push @{$context}, $1, $2;
+ $matchsub = \&matchAttrVal;
+# } elsif ($filter =~ /^\(\|\(($attrpat)=(.+)\)\(($attrpat)=(.+)\)\)$/o) {
+# $attr = $1;
+# $val = $2;
+# $attr1 = $1;
+# $val1 = $2;
+# $isand = 0;
+# } elsif ($filter =~ /^\(\&\(($attrpat)=(.+)\)\(($attrpat)=(.+)\)\)$/o) {
+# $attr = $1;
+# $val = $2;
+# $attr1 = $1;
+# $val1 = $2;
+# $isand = 1;
+# } elsif ($filter =~ /^\(\|\(($attrpat)=(.+)\)\(($attrpat)=(.+)\)\)$/o) {) {
+# # "(&(objectclass=nsBackendInstance)(|(nsslapd-suffix=$suffix)(nsslapd-suffix=$nsuffix)))");
+ }
+
+ $self->iterate($basedn, $scope, \&searchcb, [$self, $matchsub, $context]);
+}
+
+# simple searches only
+sub search {
+ my $self = shift;
+ my ($basedn, $scope, $filter, $attrsonly, @rest) = @_;
+ my $attrs;
+ if (ref($rest[0]) eq "ARRAY") {
+ $attrs = $rest[0];
+ } elsif (scalar(@rest) > 0) {
+ $attrs = \@rest;
+ }
+
+ $scope = Mozilla::LDAP::Utils::str2Scope($scope);
+
+ $self->{entries} = [];
+
+ my $ndn = normalizeDN($basedn);
+ if (!exists($self->{$ndn})) {
+ $self->setErrorCode(LDAP_NO_SUCH_OBJECT);
+ return undef;
+ }
+
+ $self->setErrorCode(0);
+ if (ref($filter) eq 'CODE') {
+ $self->iterate($basedn, $scope, \&searchcb, [$self, $filter, $attrsonly]);
+ } else {
+ $self->filterToMatchSub($basedn, $scope, $filter, $attrsonly);
+ }
+
+ return $self->nextEntry();
+}
+
+sub nextEntry {
+ my $self = shift;
+ return shift @{$self->{entries}};
+}
+
+sub add {
+ my $self = shift;
+ my $entry = shift;
+ my $dn = $entry->getDN();
+ my $ndn = normalizeDN($dn);
+ my $parentdn = getParentDN($dn);
+ my $nparentdn = normalizeDN($parentdn);
+
+ $self->setErrorCode(0);
+ if (exists($self->{$ndn})) {
+ $self->setErrorCode(LDAP_ALREADY_EXISTS);
+ return 0;
+ }
+ if ($nparentdn && !exists($self->{$nparentdn})) {
+ $self->setErrorCode(LDAP_NO_SUCH_OBJECT);
+ return 0;
+ }
+ # each hash entry has two keys
+ # data is the actual Entry
+ # children is the array ref of the one level children of this dn
+ $self->{$ndn}->{data} = $entry;
+ push @{$self->{$nparentdn}->{children}}, $self->{$ndn};
+
+ return 1;
+}
+
+sub update {
+ my $self = shift;
+ my $entry = shift;
+ my $dn = $entry->getDN();
+ my $ndn = normalizeDN($dn);
+
+ $self->setErrorCode(0);
+ if (!exists($self->{$ndn})) {
+ $self->setErrorCode(LDAP_NO_SUCH_OBJECT);
+ return 0;
+ }
+
+ $self->{$ndn}->{data} = $entry;
+
+ return 1;
+}
+
+sub delete {
+ my $self = shift;
+ my $dn = shift;
+
+ if (ref($dn)) {
+ $dn = $dn->getDN(); # an Entry
+ }
+ my $ndn = normalizeDN($dn);
+
+ $self->setErrorCode(0);
+ if (!exists($self->{$ndn})) {
+ $self->setErrorCode(LDAP_NO_SUCH_OBJECT);
+ return 0;
+ }
+
+ if (@{$self->{$ndn}->{children}}) {
+ $self->setErrorCode(LDAP_NOT_ALLOWED_ON_NONLEAF);
+ return 0;
+ }
+
+ # delete the data associated with this node
+ delete $self->{$ndn}->{data};
+ delete $self->{$ndn}->{children};
+
+ my $parentdn = getParentDN($dn);
+ my $nparentdn = normalizeDN($parentdn);
+ # delete this node from its parent
+ for (my $ii = 0; $ii < @{$self->{$nparentdn}->{children}}; ++$ii) {
+ # find matching hash ref in parent's child list
+ if ($self->{$nparentdn}->{children}->[$ii] eq $self->{$ndn}) {
+ # remove that element from the array
+ splice @{$self->{$nparentdn}->{children}}, $ii, 1;
+ # done - should only ever be one matching child
+ last;
+ }
+ }
+
+ # delete this node
+ delete $self->{$ndn};
+
+ return 0;
+}
+
+1;
diff --git a/ldap/admin/src/scripts/Resource.pm b/ldap/admin/src/scripts/Resource.pm
index 4bc52a74..1fcd44ca 100644
--- a/ldap/admin/src/scripts/Resource.pm
+++ b/ldap/admin/src/scripts/Resource.pm
@@ -112,7 +112,9 @@ sub read {
}
}
# replace \n with real newline
- $self->{res}->{$curkey} =~ s/\\n/\n/g;
+ if (defined($curkey)) {
+ $self->{res}->{$curkey} =~ s/\\n/\n/g;
+ }
close RES;
}
}
diff --git a/ldap/admin/src/scripts/Util.pm.in b/ldap/admin/src/scripts/Util.pm.in
index 008b4210..355aed73 100644
--- a/ldap/admin/src/scripts/Util.pm.in
+++ b/ldap/admin/src/scripts/Util.pm.in
@@ -119,8 +119,7 @@ sub delete_all
$conn->delete($dn);
my $rc = $conn->getErrorCode();
if ( $rc != 0 ) {
- $conn->printError();
- print "ERROR: unable to delete entry $dn, error code: $rc\n";
+ debug(1, "ERROR: unable to delete entry $dn, error code: $rc:" . $conn->getErrorString() . "\n");
return 1;
}
$dn = pop @mystack;
@@ -220,7 +219,7 @@ sub comp_entries
# $verbose prints out more info
sub check_and_add_entry
{
- my ($context, $aentry) = @_;
+ my ($context, $aentry, $errs) = @_;
my $conn = $context->[0];
my $fresh = $context->[1];
my $verbose = $context->[2];
@@ -277,6 +276,7 @@ sub check_and_add_entry
$rc = delete_all($conn, $sentry);
if ( 0 != $rc )
{
+ push @{$errs}, 'error_deleteall_entries', $sentry->{dn}, $conn->getErrorString();
debug(1, "Error deleting $sentry->{dn}\n");
return 0;
}
@@ -305,8 +305,8 @@ sub check_and_add_entry
if ( $rc != 0 )
{
my $string = $conn->getErrorString();
- print "ERROR: adding an entry $aentry->{dn} failed, error: $string\n";
- print "[entry]\n";
+ push @{$errs}, 'error_adding_entry', $aentry->{dn}, $string;
+ debug(1, "ERROR: adding an entry $aentry->{dn} failed, error: $string\n");
$aentry->printLDIF();
$conn->close();
return 0;
@@ -359,8 +359,8 @@ sub check_and_add_entry
if ( $rc != 0 )
{
my $string = $conn->getErrorString();
- print "ERROR: updating an entry $sentry->{dn} failed, error: $string\n";
- print "[entry]\n";
+ push @{$errs}, 'error_updating_entry', $sentry->{dn}, $string;
+ debug(1, "ERROR: updating an entry $sentry->{dn} failed, error: $string\n");
$aentry->printLDIF();
$conn->close();
return 0;
@@ -396,12 +396,14 @@ sub cbaddent {
# and the values are the replacements
# ldiffiles - an array ref - the list of LDIF files to
# operate on
+# errs - an array ref - this is filled in with the
+# errors encountered in processing - this is
+# suitable for passing to setup->msg or
+# Resource->getText
# callback (optional) - a code ref - a ref to a subroutine
# that will be called with each entry - see below
# context (optional) - this will be passed as the first
# argument to your given callback - see below
-# errs (optional) - an array ref - This is how errors
-# are returned to the caller - see below
# Callback:
# The callback sub will be called for each entry after
# the entry has been converted. The callback will be
@@ -413,18 +415,20 @@ sub cbaddent {
# abort processing of any further.
# Errors:
# This function should return an array of errors in the
-# format described below, for use with Resource::getText().
-# If the callback returns any errors
+# format described below, for use with Resource::getText()
+# or Setup::msg()
# Return:
# The return value is a list of entries.
# Example usage:
# sub handle_entries {
# my $context = shift;
# my $entry = shift;
+# my $errs = shift;
# .... do something with entry ....
# .... if $context is Mozilla::LDAP::Conn, $conn->add($entry); ...
# .... report errors ....
# if ($fatalerror) {
+# push @{$errs}, 'error_token', arg1, arg2, ...;
# return 0;
# } else {
# return 1;
@@ -433,14 +437,16 @@ sub cbaddent {
# $mapper = {foo => 'bar', baz => 'biff'};
# @ldiffiles = ('foo.ldif', 'bar.ldif', ..., 'biff.ldif');
# $conn = new Mozilla::LDAP::Conn(...);
-# @entries = getMappedEntries($mapper, \@ldiffiles, \&handle_entries, $conn);
+# my @errs;
+# @entries = getMappedEntries($mapper, \@ldiffiles, \@errs, \&handle_entries, $conn);
# Note that this will return 0 entries since a callback was used.
# The simpler example is this:
-# @entries = getMappedEntries($mapper, \@ldiffiles);
+# @entries = getMappedEntries($mapper, \@ldiffiles, \@errs);
#
sub getMappedEntries {
my $mapper = shift;
my $ldiffiles = shift;
+ my $errs = shift;
my $callback = shift || \&cbaddent; # default - just add entry to @entries
my @entries = ();
my $context = shift || \@entries;
@@ -451,7 +457,10 @@ sub getMappedEntries {
}
foreach my $ldiffile (@{$ldiffiles}) {
- open(MYLDIF, "< $ldiffile") or die "Can't open $ldiffile : $!";
+ if (!open(MYLDIF, "< $ldiffile")) {
+ push @{$errs}, "error_opening_ldiftmpl", $ldiffile, $!;
+ return 0;
+ }
my $in = new Mozilla::LDAP::LDIF(*MYLDIF);
debug(1, "Processing $ldiffile ...\n");
ENTRY: while (my $entry = Mozilla::LDAP::LDIF::readOneEntry($in)) {
@@ -462,9 +471,7 @@ sub getMappedEntries {
if (exists($mapper->{$1})) {
$dn =~ s{%([\w_-]+)%}{$mapper->{$1}}ge;
} else {
- print "ERROR: \"$origdn\" mapped to \"$dn\".\n";
- print "The LDIF file $ldiffile contains a token $1 for which there is no mapper.\n";
- print "Please check $ldiffile and your mapper to make sure all tokens are handled correctly.\n";
+ push @{$errs}, 'error_mapping_token_ldiftmpl', $dn, $ldiffile, $1;
$error = 1;
last ENTRY;
}
@@ -480,9 +487,8 @@ sub getMappedEntries {
if (exists($mapper->{$1})) {
$value =~ s{%([\w_-]+)%}{$mapper->{$1}}ge;
} else {
- print "ERROR: \"$origvalue\" mapped to \"$value\".\n";
- print "The LDIF file $ldiffile contains a token $1 for which there is no mapper.\n";
- print "Please check $ldiffile and your mapper to make sure all tokens are handled correctly.\n";
+ push @{$errs}, 'error_mapping_token_ldiftmpl', $dn, $ldiffile, $1;
+ debug(1, "ERROR: \"$origvalue\" mapped to \"$value\".\n");
$error = 1;
last ENTRY;
}
@@ -492,9 +498,9 @@ sub getMappedEntries {
$entry->setValues( $attr, @newvalues );
}
- if (!&{$callback}($context, $entry)) {
- print "There was an error processing entry ", $entry->getDN(), "\n";
- print "Cannot continue processing entries.\n";
+ if (!&{$callback}($context, $entry, $errs)) {
+ debug(1, "ERROR: There was an error processing entry ". $entry->getDN(). "\n");
+ debug(1, "Cannot continue processing entries.\n");
$error = 1;
last ENTRY;
}
@@ -640,7 +646,7 @@ sub addSuffix {
# The %token% tokens are replaced in getMappedEntries
sub process_maptbl
{
- my ($mapper, @infdata) = @_;
+ my ($mapper, $errs, @infdata) = @_;
if (defined($mapper->{""})) {
$mapper = $mapper->{""}; # side effect of Inf with no sections
@@ -680,7 +686,7 @@ sub process_maptbl
}
if (!defined($infsection->{$value}))
{
- print "ERROR: $value not found in the .inf files\n";
+ push @{$errs}, 'no_mapvalue_for_key', $value, $key;
return {};
}
}
@@ -709,6 +715,7 @@ sub getHashedPassword {
sub createDSInstance {
my $inf = shift;
+ my $errs = shift; # unused for now
# find ds_newinst.pl - in same directory as this script or in PATH
my $ds_newinst;
($ds_newinst = $0) =~ s|/[^/]+$|/ds_newinst.pl|;
@@ -724,13 +731,18 @@ sub createDSInstance {
}
# this creates an Inf suitable for passing to createDSInstance
+# except that it has a bogus suffix
sub createInfFromConfig {
my $configdir = shift;
my $inst = shift;
+ my $errs = shift;
my $fname = "$configdir/dse.ldif";
my $id;
($id = $inst) =~ s/^slapd-//;
- open( DSELDIF, "$fname" ) || die "Can't open $fname: $!";
+ if (!open( DSELDIF, "$fname" )) {
+ push @{$errs}, "error_opening_dseldif", $fname, $!;
+ return 0;
+ }
my ($outfh, $inffile) = tempfile(SUFFIX => '.inf');
my $in = new Mozilla::LDAP::LDIF(*DSELDIF) ;
while (my $ent = readOneEntry $in) {
diff --git a/ldap/admin/src/scripts/setup-ds.pl.in b/ldap/admin/src/scripts/setup-ds.pl.in
index 0117bdef..f52cd169 100644
--- a/ldap/admin/src/scripts/setup-ds.pl.in
+++ b/ldap/admin/src/scripts/setup-ds.pl.in
@@ -69,8 +69,10 @@ if (!$setup->{silent}) {
$setup->{inf}->write();
}
-my ($rc, $output) = createDSInstance($setup->{inf});
+my @errs;
+my ($rc, $output) = createDSInstance($setup->{inf}, \@errs);
if ($rc) {
+ $setup->msg(@errs);
$setup->msg($FATAL, 'error_creating_dsinstance', $rc, $output);
} else {
$setup->msg('created_dsinstance', $output);
diff --git a/ldap/admin/src/scripts/setup-ds.res.in b/ldap/admin/src/scripts/setup-ds.res.in
index 3c6b6fa8..4b8982e1 100644
--- a/ldap/admin/src/scripts/setup-ds.res.in
+++ b/ldap/admin/src/scripts/setup-ds.res.in
@@ -89,3 +89,9 @@ error_creating_suffix = Could not create the suffix '%s'. Error: %s\n\n
setup_exiting = Exiting . . .\nLog file is '%s'\n\n
error_creating_dsinstance = Error: Could not create directory server instance. Error code %s. Output:\n%s\n
created_dsinstance = Your new DS instance was successfully created. Output:\n%s\n
+no_mapvalue_for_key = The map value '%s' for key '%s' did not map to a value in any of the given information files.\n
+error_opening_ldiftmpl = Could not open the LDIF template file '%s'. Error: %s\n
+error_mapping_token_ldiftmpl = The entry '%s' in LDIF file '%s' contains a token '%s' for which there is no mapper.\nPlease check the file and your mapper to make sure all tokens are handled correctly.\n
+error_deleteall_entries = Error deleting entry '%s' and all children. Error: %s\n
+error_adding_entry = Error adding entry '%s'. Error: %s\n
+error_updating_entry = Error updating entry '%s'. Error: %s\n