mirror of
https://git.openldap.org/openldap/openldap.git
synced 2026-01-05 14:42:10 -05:00
Schema checking option for LDAP Sync replication
This commit is contained in:
parent
8dc1ac85dd
commit
7f882daf15
10 changed files with 65 additions and 141 deletions
|
|
@ -1112,6 +1112,7 @@ If specified multiple times, each url is provided.
|
|||
.B [searchbase=<base DN>]
|
||||
.B [filter=<filter str>]
|
||||
.B [attrs=<attr list>]
|
||||
.B [schemachecking=on|off]
|
||||
.B [scope=sub|one|base]
|
||||
.B [type=refreshOnly|refreshAndPersist]
|
||||
.B [interval=dd:hh:mm]
|
||||
|
|
@ -1155,6 +1156,19 @@ is
|
|||
The replication provider site is specified by
|
||||
.B provider
|
||||
as an LDAP URI.
|
||||
If
|
||||
.B schemachecking
|
||||
is
|
||||
.B on,
|
||||
every replicated entry will be checked for its schema
|
||||
when it is stored in the consumer replica.
|
||||
The consumer slapd should retrieve attributes of an entry
|
||||
that are required by the schema definition.
|
||||
If
|
||||
.B schemachecking
|
||||
is
|
||||
.B off,
|
||||
entries will be stored without checking the schema conformance.
|
||||
A
|
||||
.B bindmethod
|
||||
of
|
||||
|
|
|
|||
|
|
@ -2740,18 +2740,16 @@ add_syncrepl(
|
|||
|
||||
si = be->syncinfo = (syncinfo_t *) ch_calloc( 1, sizeof( syncinfo_t ) );
|
||||
|
||||
/* set default values; FIXME : add others */
|
||||
si->tls = TLS_OFF;
|
||||
if ( be->be_rootndn.bv_val )
|
||||
ber_dupbv( &si->updatedn, &be->be_rootndn );
|
||||
si->bindmethod = LDAP_AUTH_SIMPLE;
|
||||
si->lastmod = LASTMOD_NO;
|
||||
si->schemachecking = 0;
|
||||
si->filterstr = "(objectclass=*)";
|
||||
if ( be->be_suffix && be->be_suffix[0].bv_val )
|
||||
si->base = ch_strdup( be->be_suffix[0].bv_val );
|
||||
si->scope = LDAP_SCOPE_SUBTREE;
|
||||
si->attrsonly = 0;
|
||||
si->attrsexclude = 0;
|
||||
si->attrs = (char **) ch_calloc( 1, sizeof( char * ));
|
||||
si->attrs[0] = NULL;
|
||||
si->type = LDAP_SYNC_REFRESH_ONLY;
|
||||
|
|
@ -2795,7 +2793,9 @@ add_syncrepl(
|
|||
"Config: ** successfully added syncrepl \"%s\"\n",
|
||||
si->provideruri == NULL ? "(null)" : si->provideruri, 0, 0 );
|
||||
#endif
|
||||
be->be_flags |= SLAP_BFLAG_NO_SCHEMA_CHECK;
|
||||
if ( !si->schemachecking ) {
|
||||
be->be_flags |= SLAP_BFLAG_NO_SCHEMA_CHECK;
|
||||
}
|
||||
si->be = be;
|
||||
}
|
||||
}
|
||||
|
|
@ -2819,6 +2819,7 @@ add_syncrepl(
|
|||
#define STARTTLSSTR "starttls"
|
||||
#define CRITICALSTR "critical"
|
||||
|
||||
#define SCHEMASTR "schemachecking"
|
||||
#define FILTERSTR "filter"
|
||||
#define SEARCHBASESTR "searchbase"
|
||||
#define SCOPESTR "scope"
|
||||
|
|
@ -2938,17 +2939,15 @@ parse_syncrepl_line(
|
|||
free( si->srvtab );
|
||||
}
|
||||
si->srvtab = ch_strdup( val );
|
||||
} else if ( !strncasecmp( cargv[ i ], LASTMODSTR,
|
||||
sizeof( LASTMODSTR ) - 1 ) ) {
|
||||
val = cargv[ i ] + sizeof( LASTMODSTR );
|
||||
if ( !strcasecmp( val, LMREQSTR )) {
|
||||
si->lastmod = LASTMOD_REQ;
|
||||
} else if ( !strcasecmp( val, LMGENSTR )) {
|
||||
si->lastmod = LASTMOD_GEN;
|
||||
} else if ( !strcasecmp( val, LMNOSTR )) {
|
||||
si->lastmod = LASTMOD_NO;
|
||||
} else if ( !strncasecmp( cargv[ i ],
|
||||
SCHEMASTR, sizeof( SCHEMASTR ) - 1 ) ) {
|
||||
val = cargv[ i ] + sizeof( SCHEMASTR );
|
||||
if ( !strncasecmp( val, "on", sizeof( "on" ) - 1 )) {
|
||||
si->schemachecking = 1;
|
||||
} else if ( !strncasecmp( val, "off", sizeof( "off" ) - 1 ) ) {
|
||||
si->schemachecking = 0;
|
||||
} else {
|
||||
si->lastmod = -1;
|
||||
si->schemachecking = 1;
|
||||
}
|
||||
} else if ( !strncasecmp( cargv[ i ],
|
||||
FILTERSTR, sizeof( FILTERSTR ) - 1 ) ) {
|
||||
|
|
@ -2977,13 +2976,7 @@ parse_syncrepl_line(
|
|||
si->attrsonly = 1;
|
||||
} else if ( !strncasecmp( cargv[ i ],
|
||||
ATTRSSTR, sizeof( ATTRSSTR ) - 1 ) ) {
|
||||
val = cargv[ i ] + sizeof( ATTRSSTR ) - 1;
|
||||
if ( *val == '!' ) {
|
||||
si->attrsexclude = 1;
|
||||
val++;
|
||||
}
|
||||
if ( *val++ != '=' )
|
||||
continue;
|
||||
val = cargv[ i ] + sizeof( ATTRSSTR );
|
||||
str2clist( &si->attrs, val, "," );
|
||||
} else if ( !strncasecmp( cargv[ i ],
|
||||
TYPESTR, sizeof( TYPESTR ) - 1 ) ) {
|
||||
|
|
|
|||
|
|
@ -766,12 +766,10 @@ int slap_mods_opattrs(
|
|||
int mop = op->o_tag == LDAP_REQ_ADD
|
||||
? LDAP_MOD_ADD : LDAP_MOD_REPLACE;
|
||||
|
||||
syncinfo_t *si = op->o_si;
|
||||
|
||||
assert( modtail != NULL );
|
||||
assert( *modtail == NULL );
|
||||
|
||||
if ( SLAP_LASTMOD(op->o_bd) && ( !si || si->lastmod == LASTMOD_GEN )) {
|
||||
if ( SLAP_LASTMOD( op->o_bd )) {
|
||||
struct tm *ltm;
|
||||
time_t now = slap_get_time();
|
||||
|
||||
|
|
@ -824,27 +822,25 @@ int slap_mods_opattrs(
|
|||
modtail = &mod->sml_next;
|
||||
}
|
||||
|
||||
if ( SLAP_LASTMOD(op->o_bd) && ( !si || si->lastmod == LASTMOD_GEN )) {
|
||||
if ( SLAP_LASTMOD( op->o_bd )) {
|
||||
char uuidbuf[ LDAP_LUTIL_UUIDSTR_BUFSIZE ];
|
||||
|
||||
if ( !si ) {
|
||||
tmpval.bv_len = lutil_uuidstr( uuidbuf, sizeof( uuidbuf ) );
|
||||
tmpval.bv_val = uuidbuf;
|
||||
tmpval.bv_len = lutil_uuidstr( uuidbuf, sizeof( uuidbuf ) );
|
||||
tmpval.bv_val = uuidbuf;
|
||||
|
||||
mod = (Modifications *) ch_malloc( sizeof( Modifications ) );
|
||||
mod->sml_op = mop;
|
||||
mod->sml_type.bv_val = NULL;
|
||||
mod->sml_desc = slap_schema.si_ad_entryUUID;
|
||||
mod->sml_values =
|
||||
(BerVarray) ch_malloc( 2 * sizeof( struct berval ) );
|
||||
ber_dupbv( &mod->sml_values[0], &tmpval );
|
||||
mod->sml_values[1].bv_len = 0;
|
||||
mod->sml_values[1].bv_val = NULL;
|
||||
assert( mod->sml_values[0].bv_val );
|
||||
mod->sml_nvalues = NULL;
|
||||
*modtail = mod;
|
||||
modtail = &mod->sml_next;
|
||||
}
|
||||
mod = (Modifications *) ch_malloc( sizeof( Modifications ) );
|
||||
mod->sml_op = mop;
|
||||
mod->sml_type.bv_val = NULL;
|
||||
mod->sml_desc = slap_schema.si_ad_entryUUID;
|
||||
mod->sml_values =
|
||||
(BerVarray) ch_malloc( 2 * sizeof( struct berval ) );
|
||||
ber_dupbv( &mod->sml_values[0], &tmpval );
|
||||
mod->sml_values[1].bv_len = 0;
|
||||
mod->sml_values[1].bv_val = NULL;
|
||||
assert( mod->sml_values[0].bv_val );
|
||||
mod->sml_nvalues = NULL;
|
||||
*modtail = mod;
|
||||
modtail = &mod->sml_next;
|
||||
|
||||
mod = (Modifications *) ch_malloc( sizeof( Modifications ) );
|
||||
mod->sml_op = mop;
|
||||
|
|
@ -879,7 +875,7 @@ int slap_mods_opattrs(
|
|||
}
|
||||
}
|
||||
|
||||
if ( SLAP_LASTMOD(op->o_bd) && ( !si || si->lastmod == LASTMOD_GEN )) {
|
||||
if ( SLAP_LASTMOD( op->o_bd )) {
|
||||
mod = (Modifications *) ch_malloc( sizeof( Modifications ) );
|
||||
mod->sml_op = mop;
|
||||
mod->sml_type.bv_val = NULL;
|
||||
|
|
|
|||
|
|
@ -1305,16 +1305,12 @@ typedef struct syncinfo_s {
|
|||
char *authcId;
|
||||
char *authzId;
|
||||
char *srvtab;
|
||||
#define LASTMOD_REQ 0
|
||||
#define LASTMOD_GEN 1
|
||||
#define LASTMOD_NO 2
|
||||
int lastmod;
|
||||
int schemachecking;
|
||||
Filter *filter;
|
||||
char *filterstr;
|
||||
char *base;
|
||||
int scope;
|
||||
int attrsonly;
|
||||
int attrsexclude;
|
||||
char **attrs;
|
||||
int type;
|
||||
time_t interval;
|
||||
|
|
|
|||
|
|
@ -45,45 +45,18 @@ static int nonpresent_callback( struct slap_op *, struct slap_rep * );
|
|||
static int null_callback( struct slap_op *, struct slap_rep * );
|
||||
static int contextcsn_callback( Operation*, SlapReply* );
|
||||
|
||||
static AttributeDescription **add_descs;
|
||||
static AttributeDescription **add_descs_lastmod;
|
||||
static AttributeDescription **del_descs;
|
||||
static AttributeDescription **del_descs_lastmod;
|
||||
static AttributeDescription **sync_descs;
|
||||
|
||||
struct runqueue_s syncrepl_rq;
|
||||
|
||||
void
|
||||
init_syncrepl()
|
||||
{
|
||||
add_descs = ch_malloc( 2 * sizeof( AttributeDescription * ));
|
||||
add_descs[0] = slap_schema.si_ad_objectClass;
|
||||
add_descs[1] = NULL;
|
||||
|
||||
add_descs_lastmod = ch_malloc( 7 * sizeof( AttributeDescription * ));
|
||||
add_descs_lastmod[0] = slap_schema.si_ad_objectClass;
|
||||
add_descs_lastmod[1] = slap_schema.si_ad_creatorsName;
|
||||
add_descs_lastmod[2] = slap_schema.si_ad_modifiersName;
|
||||
add_descs_lastmod[3] = slap_schema.si_ad_createTimestamp;
|
||||
add_descs_lastmod[4] = slap_schema.si_ad_modifyTimestamp;
|
||||
add_descs_lastmod[5] = slap_schema.si_ad_entryCSN;
|
||||
add_descs_lastmod[6] = NULL;
|
||||
|
||||
del_descs = ch_malloc( 9 * sizeof( AttributeDescription * ));
|
||||
del_descs[0] = slap_schema.si_ad_structuralObjectClass;
|
||||
del_descs[1] = slap_schema.si_ad_subschemaSubentry;
|
||||
del_descs[2] = slap_schema.si_ad_hasSubordinates;
|
||||
del_descs[3] = slap_schema.si_ad_creatorsName;
|
||||
del_descs[4] = slap_schema.si_ad_modifiersName;
|
||||
del_descs[5] = slap_schema.si_ad_createTimestamp;
|
||||
del_descs[6] = slap_schema.si_ad_modifyTimestamp;
|
||||
del_descs[7] = slap_schema.si_ad_entryCSN;
|
||||
del_descs[8] = NULL;
|
||||
|
||||
del_descs_lastmod = ch_malloc( 4 * sizeof( AttributeDescription * ));
|
||||
del_descs_lastmod[0] = slap_schema.si_ad_structuralObjectClass;
|
||||
del_descs_lastmod[1] = slap_schema.si_ad_subschemaSubentry;
|
||||
del_descs_lastmod[2] = slap_schema.si_ad_hasSubordinates;
|
||||
del_descs_lastmod[3] = NULL;
|
||||
sync_descs = ch_malloc( 4 * sizeof( AttributeDescription * ));
|
||||
sync_descs[0] = slap_schema.si_ad_objectClass;
|
||||
sync_descs[1] = slap_schema.si_ad_structuralObjectClass;
|
||||
sync_descs[2] = slap_schema.si_ad_entryCSN;
|
||||
sync_descs[3] = NULL;
|
||||
}
|
||||
|
||||
int
|
||||
|
|
@ -430,11 +403,7 @@ do_syncrepl(
|
|||
psub = be->be_nsuffix[0];
|
||||
|
||||
/* Delete Attributes */
|
||||
if ( si->lastmod == LASTMOD_REQ ) {
|
||||
descs = del_descs_lastmod;
|
||||
} else {
|
||||
descs = del_descs;
|
||||
}
|
||||
descs = sync_descs;
|
||||
|
||||
for ( i = 0; descs[i] != NULL; i++ ) {
|
||||
for ( j = 0; si->attrs[j] != NULL; j++ ) {
|
||||
|
|
@ -451,15 +420,11 @@ do_syncrepl(
|
|||
|
||||
for ( n = 0; si->attrs[ n ] != NULL; n++ ) ;
|
||||
|
||||
if ( si->lastmod == LASTMOD_REQ ) {
|
||||
descs = add_descs_lastmod;
|
||||
} else {
|
||||
descs = add_descs;
|
||||
}
|
||||
descs = sync_descs;
|
||||
|
||||
for ( i = 0; descs[i] != NULL; i++ ) {
|
||||
tmp = ( char ** ) ch_realloc( si->attrs,
|
||||
( n + 2 ) * sizeof( char * ));
|
||||
( n + 3 ) * sizeof( char * ));
|
||||
if ( tmp == NULL ) {
|
||||
#ifdef NEW_LOGGING
|
||||
LDAP_LOG( OPERATION, ERR, "out of memory\n", 0,0,0 );
|
||||
|
|
@ -719,8 +684,6 @@ syncrepl_message_to_entry(
|
|||
|
||||
ber_tag_t tag;
|
||||
|
||||
Modifications *prevml = NULL;
|
||||
Modifications *nextml = NULL;
|
||||
Modifications *ml = NULL;
|
||||
AttributeDescription** descs;
|
||||
int i;
|
||||
|
|
@ -857,29 +820,6 @@ syncrepl_message_to_entry(
|
|||
|
||||
ad = ml->sml_desc;
|
||||
ml->sml_desc = NULL;
|
||||
|
||||
if ( si->lastmod == LASTMOD_REQ ) {
|
||||
descs = del_descs_lastmod;
|
||||
} else {
|
||||
descs = del_descs;
|
||||
}
|
||||
|
||||
for ( i = 0; descs[i] != NULL; i++ ) {
|
||||
if ( ad == descs[i] ) {
|
||||
if ( prevml == NULL ) {
|
||||
modlist = &ml->sml_next;
|
||||
prevml = NULL;
|
||||
} else {
|
||||
prevml->sml_next = ml->sml_next;
|
||||
}
|
||||
slap_mod_free( &ml->sml_mod, 0 );
|
||||
nextml = ml->sml_next;
|
||||
free( ml );
|
||||
ml = nextml;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
prevml = ml;
|
||||
ml = ml->sml_next;
|
||||
}
|
||||
|
||||
|
|
@ -896,20 +836,6 @@ syncrepl_message_to_entry(
|
|||
return NULL;
|
||||
}
|
||||
|
||||
rc = slap_mods_opattrs( op, *modlist, modtail,
|
||||
&text,txtbuf, textlen );
|
||||
|
||||
if( rc != LDAP_SUCCESS ) {
|
||||
#ifdef NEW_LOGGING
|
||||
LDAP_LOG( OPERATION, ERR,
|
||||
"syncrepl_message_to_entry: mods opattrs (%s)\n", text, 0, 0 );
|
||||
#else
|
||||
Debug( LDAP_DEBUG_ANY, "syncrepl_message_to_entry: mods opattrs (%s)\n",
|
||||
text, 0, 0 );
|
||||
#endif
|
||||
return NULL;
|
||||
}
|
||||
|
||||
rc = slap_mods2entry( *modlist, &e, 1, 1, &text, txtbuf, textlen);
|
||||
if( rc != LDAP_SUCCESS ) {
|
||||
#ifdef NEW_LOGGING
|
||||
|
|
@ -1037,9 +963,8 @@ syncrepl_entry(
|
|||
rc == LDAP_REFERRAL ||
|
||||
rc == LDAP_NO_SUCH_OBJECT ) {
|
||||
|
||||
if ( !attr_find( e->e_attrs, slap_schema.si_ad_entryUUID )) {
|
||||
attr_merge_normalize_one( e, slap_schema.si_ad_entryUUID, syncUUID, op->o_tmpmemctx );
|
||||
}
|
||||
attr_delete( &e->e_attrs, slap_schema.si_ad_entryUUID );
|
||||
attr_merge_normalize_one( e, slap_schema.si_ad_entryUUID, syncUUID, op->o_tmpmemctx );
|
||||
|
||||
op->o_tag = LDAP_REQ_ADD;
|
||||
op->ora_e = e;
|
||||
|
|
@ -1447,8 +1372,7 @@ syncrepl_updateCookie(
|
|||
|
||||
for ( ml = modlist; ml != NULL; ml = mlnext ) {
|
||||
mlnext = ml->sml_next;
|
||||
if ( ml->sml_desc == slap_schema.si_ad_structuralObjectClass )
|
||||
ml->sml_op = LDAP_MOD_REPLACE;
|
||||
ml->sml_op = LDAP_MOD_REPLACE;
|
||||
}
|
||||
|
||||
if( rc != LDAP_SUCCESS ) {
|
||||
|
|
@ -1494,6 +1418,7 @@ update_cookie_retry:
|
|||
op->o_tag = LDAP_REQ_MODIFY;
|
||||
op->orm_modlist = modlist;
|
||||
rc = be->be_modify( op, &rs );
|
||||
|
||||
if ( rc != LDAP_SUCCESS ) {
|
||||
if ( rc == LDAP_REFERRAL ||
|
||||
rc == LDAP_NO_SUCH_OBJECT ) {
|
||||
|
|
|
|||
|
|
@ -39,6 +39,6 @@ syncrepl id=1
|
|||
searchbase="o=University of Michigan,c=US"
|
||||
filter="(objectClass=*)"
|
||||
attrs="*"
|
||||
lastmod=req
|
||||
schemachecking=off
|
||||
scope=sub
|
||||
type=refreshAndPersist
|
||||
|
|
|
|||
|
|
@ -39,6 +39,6 @@ syncrepl id=1
|
|||
searchbase="o=University of Michigan,c=US"
|
||||
filter="(objectClass=*)"
|
||||
attrs="*"
|
||||
lastmod=req
|
||||
schemachecking=off
|
||||
scope=sub
|
||||
type=refreshAndPersist
|
||||
|
|
|
|||
|
|
@ -39,6 +39,6 @@ syncrepl id=1
|
|||
searchbase="o=University of Michigan,c=US"
|
||||
filter="(objectClass=*)"
|
||||
attrs="*"
|
||||
lastmod=req
|
||||
schemachecking=off
|
||||
scope=sub
|
||||
type=refreshAndPersist
|
||||
|
|
|
|||
|
|
@ -39,7 +39,7 @@ syncrepl id=1
|
|||
searchbase="o=University of Michigan,c=US"
|
||||
filter="(objectClass=*)"
|
||||
attrs="*"
|
||||
lastmod=req
|
||||
schemachecking=off
|
||||
scope=sub
|
||||
type=refreshOnly
|
||||
interval=00:00:01
|
||||
|
|
|
|||
|
|
@ -39,7 +39,7 @@ syncrepl id=1
|
|||
searchbase="o=University of Michigan,c=US"
|
||||
filter="(objectClass=*)"
|
||||
attrs="*"
|
||||
lastmod=req
|
||||
schemachecking=off
|
||||
scope=sub
|
||||
type=refreshOnly
|
||||
interval=00:00:01
|
||||
|
|
|
|||
Loading…
Reference in a new issue