Start line:  
End line:  

Snippet Preview

Snippet HTML Code

Stack Overflow Questions
  /*
   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
   *
   * Copyright 2011 Tirasa. All rights reserved.
   *
   * The contents of this file are subject to the terms of either the GNU
   * General Public License Version 2 only ("GPL") or the Common Development
   * and Distribution License("CDDL") (collectively, the "License").  You
   * may not use this file except in compliance with the License. You can obtain
  * a copy of the License at https://glassfish.dev.java.net/public/CDDL+GPL.html
  * or glassfish/bootstrap/legal/LICENSE.txt.  See the License for the specific
  * language governing permissions and limitations under the License.
  *
  * When distributing the software, include this License Header Notice in each
  * file and include the License file at glassfish/bootstrap/legal/LICENSE.txt.
  * Sun designates this particular file as subject to the "Classpath" exception
  * as provided by Sun in the GPL Version 2 section of the License file that
  * accompanied this code.  If applicable, add the following below the License
  * Header, with the fields enclosed by brackets [] replaced by your own
  * identifying information: "Portions Copyrighted [year]
  * [name of copyright owner]"
  */
 package org.connid.ad.sync;
 
 import  com.sun.jndi.ldap.ctl.DirSyncResponseControl;
 import java.util.Map;
 import java.util.Set;
An implementation of the sync operation based on the DirSync protocol, for Active Directory.
 
 public class ADSyncStrategy {
 
     private static final Log LOG = Log.getLog(ADSyncStrategy.class);
 
     private final transient ADConnection conn;
 
     private transient SyncToken latestSyncToken;
 
     public ADSyncStrategy(final ADConnection conn) {
 
         this. = conn;
     }
 
     private Map<StringSet<SearchResult>> search(
             final LdapContext ctx,
             final String filter,
             final SearchControls searchCtls,
             final boolean updateLastSyncToken) {
 
         final Map<StringSet<SearchResult>> result =
                 new HashMap<StringSet<SearchResult>>();
 
         for (String baseContextDn :
                 .getConfiguration().getBaseContextsToSynchronize()) {
 
             if (.isOk()) {
                 .ok("Searching from " + baseContextDn);
             }
 
             if (!result.containsKey(baseContextDn)) {
                 result.put(baseContextDnnew HashSet<SearchResult>());
             }
 
             try {
                 final NamingEnumeration<SearchResultanswer =
                         ctx.search(baseContextDnfiltersearchCtls);
 
                 while (answer.hasMoreElements()) {
                    result.get(baseContextDn).add(answer.nextElement());
                }
                if (.isOk()) {
                    .ok("Search found {0} items",
                            result.get(baseContextDn).size());
                }
                if (updateLastSyncToken) {
                    final Control[] rspCtls = ctx.getResponseControls();
                    if (rspCtls != null) {
                        if (.isOk()) {
                            .ok("Response Controls: {0}"rspCtls.length);
                        }
                        for (int i = 0; i < rspCtls.lengthi++) {
                            if (rspCtls[iinstanceof DirSyncResponseControl) {
                                DirSyncResponseControl dirSyncRspCtl =
                                        (DirSyncResponseControl) rspCtls[i];
                                 =
                                        new SyncToken(dirSyncRspCtl.getCookie());
                            }
                        }
                        if (.isOk()) {
                            .ok("Latest sync token set to {0}",
                                    );
                        }
                    }
                }
            } catch (NamingException e) {
                .error(e"While searching base context {0} with filter {1} "
                        + "and search controls {2}",
                        baseContextDnfilter.toString(), searchCtls);
            }
        }
        return result;
    }
    public void sync(
            final SyncToken token,
            final SyncResultsHandler handler,
            final OperationOptions options,
            final ObjectClass oclass) {
        // -----------------------------------
        // Create search filter
        // -----------------------------------
        final String filter = DirSyncUtils.createDirSyncFilter(
                (ADConfiguration.getConfiguration());
        if (.isOk()) {
            .ok("Search filter: " + filter);
        }
        // -----------------------------------
        // -----------------------------------
        // Create search control
        // -----------------------------------
        final SearchControls searchCtls =
                LdapInternalSearch.createDefaultSearchControls();
        searchCtls.setSearchScope(.);
        searchCtls.setReturningAttributes(null);
        // -----------------------------------
        // -----------------------------------
        // Get Synchronization Context
        // -----------------------------------
        final LdapContext ctx;
        try {
            if (token == null
                    || token.getValue() == null
                    || !(token.getValue() instanceof byte[])
                    || ((byte[]) token.getValue()).length == 0) {
                if (.isOk()) {
                    .ok("Synchronization with empty token.");
                }
                ctx = .getSyncContext(new Control[]{new DirSyncControl()});
            } else {
                if (.isOk()) {
                    .ok("Synchronization with token.");
                }
                ctx = .getSyncContext(new Control[]{
                            new DirSyncControl((byte[]) token.getValue())});
            }
        } catch (Exception e) {
            throw new ConnectorException(
                    "Could not set DirSync request controls"e);
        }
        // -----------------------------------
        final Map<StringSet<SearchResult>> changes =
                search(ctxfiltersearchCtlstrue);
        for (String baseDN :
                .getConfiguration().getBaseContextsToSynchronize()) {
            if (changes.containsKey(baseDN)) {
                for (SearchResult sr : changes.get(baseDN)) {
                    try {
                        handleSyncDelta(
                                oclass,
                                ctx,
                                sr,
                                handler);
                    } catch (NamingException e) {
                        .error(e"SyncDelta handling for '{0}' failed",
                                sr.getName());
                    }
                }
            }
        }
    }
    public SyncToken getLatestSyncToken() {
        return ;
    }
    private void handleSyncDelta(
            final ObjectClass oclass,
            final LdapContext ctx,
            final SearchResult sr,
            final SyncResultsHandler handler)
            throws NamingException {
        if (ctx == null || sr == null) {
            throw new ConnectorException("Invalid context or search result.");
        }
        ctx.setRequestControls(new Control[]{new DeletedControl()});
        // Just used to retrieve object classes and to pass to getSyncDelta
        Attributes profile = sr.getAttributes();
        if (.isOk()) {
            .ok("Object profile: {0}"profile);
        }
        final Set<Stringclasses = CollectionUtil.newCaseInsensitiveSet();
        String guid = DirSyncUtils.getGuidAsString(
                (byte[]) profile.get("objectGUID").get());
        boolean isDeleted = false;
        try {
            javax.naming.directory.Attribute attributeIsDeleted =
                    profile.get("isDeleted");
            isDeleted =
                    attributeIsDeleted != null
                    && attributeIsDeleted.get() != null
                    && Boolean.parseBoolean(
                    attributeIsDeleted.get().toString());
        } catch (NoSuchElementException e) {
            if (.isOk()) {
                .ok("Cannot find the isDeleted element for user.");
            }
        } catch (Throwable t) {
            .error(t"Error retrieving isDeleted attribute");
        }
        // We need for this beacause DirSync can return an uncomplete profile.
        profile = ctx.getAttributes("<GUID=" + guid + ">");
        final NamingEnumeration<StringobjectClasses =
                (NamingEnumeration<String>) profile.get("objectClass").getAll();
        while (objectClasses.hasMoreElements()) {
            classes.add(objectClasses.next());
        }
        final ADConfiguration conf = (ADConfiguration.getConfiguration();
        final javax.naming.directory.Attribute member11;
        final javax.naming.directory.Attribute member00;
        if (classes.contains("group")) {
            // search for users in adn users out
            if (.isOk()) {
                .ok("Modified group {0}"sr.getNameInNamespace());
            }
            member11 = sr.getAttributes().get("member;range=1-1");
            member00 = sr.getAttributes().get("member;range=0-0");
            ctx.setRequestControls(null);
            String userDN;
            if (member11 != null && !conf.isLoading()) {
                if (.isOk()) {
                    .ok("Found users 'IN' ...");
                }
                // users to be created/updated
                final NamingEnumeration<StringuserDNs =
                        (NamingEnumeration<String>) member11.getAll();
                while (userDNs.hasMoreElements()) {
                    // for each new user "in" we must verify custom ldap filter
                    userDN = userDNs.next();
                    if (DirSyncUtils.verifyFilter(ctxuserDNconf)) {
                        if (.isOk()) {
                            .ok("IN user {0}"userDN);
                        }
                        profile = ctx.getAttributes(userDN);
                        guid = DirSyncUtils.getGuidAsString(
                                (byte[]) profile.get("objectGUID").get());
                        handler.handle(getSyncDelta(
                                oclass,
                                userDN,
                                .,
                                profile));
                    }
                }
            }
            if (member00 != null && conf.isRetrieveDeletedUser()) {
                // users to be removed
                if (.isOk()) {
                    .ok("Found users 'OUT' ...");
                }
                final NamingEnumeration<StringuserDNs =
                        (NamingEnumeration<String>) member00.getAll();
                while (userDNs.hasMoreElements()) {
                    // for each user "out" we must verify custom ldap filter
                    userDN = userDNs.next();
                    profile = ctx.getAttributes(userDN);
                    guid = DirSyncUtils.getGuidAsString(
                            (byte[]) profile.get("objectGUID").get());
                    SyncDeltaType deltaType;
                    if (!DirSyncUtils.verifyFilter(ctxuserDNconf)) {
                        if (.isOk()) {
                            .ok("OUT user {0} - delete"userDN);
                        }
                        deltaType = .;
                    } else {
                        // update user i order to update memberOf
                        // issue http://code.google.com/p/connid/issues/detail?id=25
                        if (.isOk()) {
                            .ok("OUT user {0} - update"userDN);
                        }
                        deltaType = .;
                    }
                    handler.handle(getSyncDelta(
                            oclass,
                            userDN,
                            deltaType,
                            profile));
                }
            }
        } else if (classes.contains("user")) {
            if (.isOk()) {
                .ok("Created/Updated/Deleted user {0}",
                        sr.getNameInNamespace());
            }
            if (isDeleted) {
                if (.isOk()) {
                    .ok("Deleted user {0}"sr.getNameInNamespace());
                }
                handler.handle(getSyncDelta(
                        oclass,
                        sr.getNameInNamespace(),
                        .,
                        profile));
            } else {
                // user to be created/updated
                if (.isOk()) {
                    .ok("Created/Updated user {0}"sr.getNameInNamespace());
                }
                if (DirSyncUtils.verifyFilter(
                        ctxsr.getNameInNamespace(), conf)) {
                    if (.isOk()) {
                        .ok("Matched user {0}"sr.getNameInNamespace());
                    }
                    handler.handle(getSyncDelta(
                            oclass,
                            sr.getNameInNamespace(),
                            .,
                            profile));
                } else {
                    if (.isOk()) {
                        .ok("Ignore changes about user {0}",
                                sr.getNameInNamespace());
                    }
                }
            }
        } else {
            if (.isInfo()) {
                .info("Invalid object type {0}"classes);
            }
        }
    }
    private SyncDelta getSyncDelta(
            final ObjectClass oclass,
            final String entryDN,
            final SyncDeltaType syncDeltaType,
            final Attributes profile)
            throws NamingException {
        final SyncDeltaBuilder sdb = new SyncDeltaBuilder();
        // Set token
        sdb.setToken();
        // Set Delta Type
        sdb.setDeltaType(syncDeltaType);
        javax.naming.directory.Attribute uidAttribute;
        Uid uid = null;
        if (StringUtil.isNotBlank(.getConfiguration().getUidAttribute())) {
            uidAttribute =
                    profile.get(.getConfiguration().getUidAttribute());
            if (uidAttribute != null) {
                uid = new Uid(uidAttribute.get().toString());
            }
        }
        if (uid == null) {
            throw new ConnectorException("UID attribute not found");
        }
        // Set UID
        sdb.setUid(uid);
        // Set Connector Object
        if (. != syncDeltaType) {
            sdb.setObject(new ADUtilities((ADConnection).
                    createConnectorObject(entryDNprofileoclass));
        }
        return sdb.build();
    }
New to GrepCode? Check out our FAQ X