You are viewing a plain text version of this content. The canonical link for it is here.
Posted to oak-commits@jackrabbit.apache.org by tr...@apache.org on 2016/06/08 21:24:45 UTC

svn commit: r1747456 - in /jackrabbit/oak/branches/1.2/oak-auth-external/src: main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/ main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/ main/java/org/apache...

Author: tripod
Date: Wed Jun  8 21:24:45 2016
New Revision: 1747456

URL: http://svn.apache.org/viewvc?rev=1747456&view=rev
Log:
OAK-3508 External login module should reduce LDAP lookups for pre-authenticated users

Added:
    jackrabbit/oak/branches/1.2/oak-auth-external/src/test/java/org/apache/jackrabbit/oak/spi/security/authentication/external/DefaultSyncHandlerTest.java
Modified:
    jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/SyncHandler.java
    jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncContext.java
    jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncedIdentity.java
    jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/DefaultSyncHandler.java
    jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/ExternalLoginModule.java
    jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/jmx/SyncMBeanImpl.java
    jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/package-info.java

Modified: jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/SyncHandler.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/SyncHandler.java?rev=1747456&r1=1747455&r2=1747456&view=diff
==============================================================================
--- jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/SyncHandler.java (original)
+++ jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/SyncHandler.java Wed Jun  8 21:24:45 2016
@@ -70,6 +70,13 @@ public interface SyncHandler {
     SyncedIdentity findIdentity(@Nonnull UserManager userManager, @Nonnull String id) throws RepositoryException;
 
     /**
+     * Checks if the identity requires sync based on the configuration, type and last sync time.
+     * @param identity the identity to check
+     * @return {@code true} if the identity requires synchronization.
+     */
+    boolean requiresSync(@Nonnull SyncedIdentity identity);
+
+    /**
      * Lists all externally synced identities.
      * @param userManager the user manager
      * @return an iterator over all authorizable that are externally synced.
@@ -77,4 +84,5 @@ public interface SyncHandler {
      */
     @Nonnull
     Iterator<SyncedIdentity> listIdentities(@Nonnull UserManager userManager) throws RepositoryException;
+
 }
\ No newline at end of file

Modified: jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncContext.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncContext.java?rev=1747456&r1=1747455&r2=1747456&view=diff
==============================================================================
--- jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncContext.java (original)
+++ jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncContext.java Wed Jun  8 21:24:45 2016
@@ -115,17 +115,16 @@ public class DefaultSyncContext implemen
      */
     @CheckForNull
     public static DefaultSyncedIdentity createSyncedIdentity(@Nullable Authorizable auth) throws RepositoryException {
-        ExternalIdentityRef ref = (auth == null) ? null : getIdentityRef(auth);
-        if (ref == null) {
+        if (auth == null) {
             return null;
-        } else {
-            Value[] lmValues = auth.getProperty(REP_LAST_SYNCED);
-            long lastModified = -1;
-            if (lmValues != null && lmValues.length > 0) {
-                lastModified = lmValues[0].getLong();
-            }
-            return new DefaultSyncedIdentity(auth.getID(), ref, auth.isGroup(), lastModified);
         }
+        ExternalIdentityRef ref = getIdentityRef(auth);
+        Value[] lmValues = auth.getProperty(REP_LAST_SYNCED);
+        long lastModified = -1;
+        if (lmValues != null && lmValues.length > 0) {
+            lastModified = lmValues[0].getLong();
+        }
+        return new DefaultSyncedIdentity(auth.getID(), ref, auth.isGroup(), lastModified);
     }
 
     /**

Modified: jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncedIdentity.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncedIdentity.java?rev=1747456&r1=1747455&r2=1747456&view=diff
==============================================================================
--- jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncedIdentity.java (original)
+++ jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/basic/DefaultSyncedIdentity.java Wed Jun  8 21:24:45 2016
@@ -67,7 +67,7 @@ public class DefaultSyncedIdentity imple
 
     @Override
     public String toString() {
-        final StringBuilder sb = new StringBuilder("SyncedIdentityImpl{");
+        final StringBuilder sb = new StringBuilder("DefaultSyncedIdentity{");
         sb.append("id='").append(id).append('\'');
         sb.append(", ref=").append(ref);
         sb.append(", isGroup=").append(isGroup);

Modified: jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/DefaultSyncHandler.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/DefaultSyncHandler.java?rev=1747456&r1=1747455&r2=1747456&view=diff
==============================================================================
--- jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/DefaultSyncHandler.java (original)
+++ jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/DefaultSyncHandler.java Wed Jun  8 21:24:45 2016
@@ -118,6 +118,21 @@ public class DefaultSyncHandler implemen
     /**
      * {@inheritDoc}
      */
+    @Override
+    public boolean requiresSync(@Nonnull SyncedIdentity identity) {
+        if (identity.getExternalIdRef() == null || identity.lastSynced() < 0) {
+            return true;
+        }
+        final long now = System.currentTimeMillis();
+        final long expirationTime = identity.isGroup()
+                ? config.group().getExpirationTime()
+                : config.user().getExpirationTime();
+        return now - identity.lastSynced() > expirationTime;
+    }
+
+    /**
+     * {@inheritDoc}
+     */
     @Nonnull
     @Override
     public Iterator<SyncedIdentity> listIdentities(@Nonnull UserManager userManager) throws RepositoryException {

Modified: jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/ExternalLoginModule.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/ExternalLoginModule.java?rev=1747456&r1=1747455&r2=1747456&view=diff
==============================================================================
--- jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/ExternalLoginModule.java (original)
+++ jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/ExternalLoginModule.java Wed Jun  8 21:24:45 2016
@@ -212,6 +212,10 @@ public class ExternalLoginModule extends
             }
 
             if (preAuthLogin != null) {
+                if (sId != null && !syncHandler.requiresSync(sId)) {
+                    log.debug("pre-authenticated external user {} does not require syncing.", sId);
+                    return false;
+                }
                 externalUser = idp.getUser(preAuthLogin.getUserId());
             } else {
                 externalUser = idp.authenticate(credentials);

Modified: jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/jmx/SyncMBeanImpl.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/jmx/SyncMBeanImpl.java?rev=1747456&r1=1747455&r2=1747456&view=diff
==============================================================================
--- jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/jmx/SyncMBeanImpl.java (original)
+++ jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/impl/jmx/SyncMBeanImpl.java Wed Jun  8 21:24:45 2016
@@ -316,10 +316,10 @@ public class SyncMBeanImpl implements Sy
         }
 
         private boolean isMyIDP(SyncedIdentity id) {
-            String idpName = id.getExternalIdRef() == null
+            String providerName = id.getExternalIdRef() == null
                     ? null
                     : id.getExternalIdRef().getProviderName();
-            return (idpName == null || idpName.length() ==0 || idpName.equals(idp.getName()));
+            return providerName != null && (providerName.isEmpty() || providerName.equals(idp.getName()));
         }
     }
 

Modified: jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/package-info.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/package-info.java?rev=1747456&r1=1747455&r2=1747456&view=diff
==============================================================================
--- jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/package-info.java (original)
+++ jackrabbit/oak/branches/1.2/oak-auth-external/src/main/java/org/apache/jackrabbit/oak/spi/security/authentication/external/package-info.java Wed Jun  8 21:24:45 2016
@@ -14,7 +14,7 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-@Version("1.0")
+@Version("2.0.0")
 @Export
 package org.apache.jackrabbit.oak.spi.security.authentication.external;
 

Added: jackrabbit/oak/branches/1.2/oak-auth-external/src/test/java/org/apache/jackrabbit/oak/spi/security/authentication/external/DefaultSyncHandlerTest.java
URL: http://svn.apache.org/viewvc/jackrabbit/oak/branches/1.2/oak-auth-external/src/test/java/org/apache/jackrabbit/oak/spi/security/authentication/external/DefaultSyncHandlerTest.java?rev=1747456&view=auto
==============================================================================
--- jackrabbit/oak/branches/1.2/oak-auth-external/src/test/java/org/apache/jackrabbit/oak/spi/security/authentication/external/DefaultSyncHandlerTest.java (added)
+++ jackrabbit/oak/branches/1.2/oak-auth-external/src/test/java/org/apache/jackrabbit/oak/spi/security/authentication/external/DefaultSyncHandlerTest.java Wed Jun  8 21:24:45 2016
@@ -0,0 +1,141 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.jackrabbit.oak.spi.security.authentication.external;
+
+import java.util.Calendar;
+
+import javax.jcr.SimpleCredentials;
+import javax.jcr.Value;
+import javax.jcr.ValueFactory;
+
+import org.apache.jackrabbit.api.security.user.Authorizable;
+import org.apache.jackrabbit.api.security.user.UserManager;
+import org.apache.jackrabbit.oak.namepath.NamePathMapper;
+import org.apache.jackrabbit.oak.plugins.value.ValueFactoryImpl;
+import org.apache.jackrabbit.oak.spi.security.authentication.external.basic.DefaultSyncConfig;
+import org.apache.jackrabbit.oak.spi.security.authentication.external.basic.DefaultSyncContext;
+import org.junit.After;
+import org.junit.Before;
+import org.junit.Test;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertNull;
+import static org.junit.Assert.assertTrue;
+
+/**
+ * DefaultSyncHandlerTest
+ */
+public class DefaultSyncHandlerTest extends ExternalLoginModuleTestBase {
+
+    private final String userId = "testUser";
+
+    @Before
+    public void before() throws Exception {
+        super.before();
+    }
+
+    @After
+    public void after() throws Exception {
+        super.after();
+    }
+
+    protected ExternalIdentityProvider createIDP() {
+        return new TestIdentityProvider();
+    }
+
+    @Override
+    protected void destroyIDP(ExternalIdentityProvider idp) {
+    // ignore
+    }
+
+    @Override
+    protected void setSyncConfig(DefaultSyncConfig cfg) {
+        if (cfg != null) {
+            cfg.user().setExpirationTime(500);
+        }
+        super.setSyncConfig(cfg);
+    }
+
+    @Test
+    public void testFindMissingIdentity() throws Exception {
+        UserManager userManager = getUserManager(root);
+        SyncHandler mgr = syncManager.getSyncHandler("default");
+        SyncedIdentity id = mgr.findIdentity(userManager, "foobar");
+        assertNull("unknown authorizable should not exist", id);
+    }
+
+    @Test
+    public void testFindLocalIdentity() throws Exception {
+        UserManager userManager = getUserManager(root);
+        SyncHandler mgr = syncManager.getSyncHandler("default");
+        SyncedIdentity id = mgr.findIdentity(userManager, "admin");
+        assertNotNull("known authorizable should exist", id);
+        assertNull("local user should not have external ref", id.getExternalIdRef());
+    }
+
+    @Test
+    public void testFindExternalIdentity() throws Exception {
+        login(new SimpleCredentials(userId, new char[0])).close();
+        root.refresh();
+
+        UserManager userManager = getUserManager(root);
+        SyncHandler mgr = syncManager.getSyncHandler("default");
+        SyncedIdentity id = mgr.findIdentity(userManager, userId);
+        assertNotNull("known authorizable should exist", id);
+        assertEquals("external user should have correct external ref.idp", idp.getName(), id.getExternalIdRef().getProviderName());
+        assertEquals("external user should have correct external ref.id", userId, id.getExternalIdRef().getId());
+    }
+
+    @Test
+    public void testRequiresNoSync() throws Exception {
+        login(new SimpleCredentials(userId, new char[0])).close();
+        root.refresh();
+
+        UserManager userManager = getUserManager(root);
+        SyncHandler mgr = syncManager.getSyncHandler("default");
+        SyncedIdentity id = mgr.findIdentity(userManager, userId);
+        assertNotNull("known authorizable should exist", id);
+
+        assertFalse("freshly synced id should not require sync", mgr.requiresSync(id));
+    }
+
+    @Test
+    public void testRequiresSync() throws Exception {
+        login(new SimpleCredentials(userId, new char[0])).close();
+        root.refresh();
+
+        ValueFactory valueFactory = new ValueFactoryImpl(root, NamePathMapper.DEFAULT);
+        final Calendar nowCal = Calendar.getInstance();
+        nowCal.setTimeInMillis(nowCal.getTimeInMillis() - 1000);
+        Value nowValue = valueFactory.createValue(nowCal);
+
+        UserManager userManager = getUserManager(root);
+        Authorizable a = userManager.getAuthorizable(userId);
+        a.setProperty(DefaultSyncContext.REP_LAST_SYNCED, nowValue);
+        root.commit();
+
+        SyncHandler mgr = syncManager.getSyncHandler("default");
+        SyncedIdentity id = mgr.findIdentity(userManager, userId);
+        assertNotNull("known authorizable should exist", id);
+
+        assertTrue("synced id should require sync", mgr.requiresSync(id));
+    }
+
+
+}
\ No newline at end of file