Author: kwright
Date: Wed Oct 23 12:45:31 2013
New Revision: 1535006

URL: http://svn.apache.org/r1535006
Log:
Flesh out multi-domain requests to authority service

Modified:
    
manifoldcf/branches/CONNECTORS-792/framework/authority-servlet/src/main/java/org/apache/manifoldcf/authorityservlet/UserACLServlet.java
    
manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/authority/AuthorityConnectionManager.java
    
manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/interfaces/IAuthorityConnectionManager.java

Modified: 
manifoldcf/branches/CONNECTORS-792/framework/authority-servlet/src/main/java/org/apache/manifoldcf/authorityservlet/UserACLServlet.java
URL: 
http://svn.apache.org/viewvc/manifoldcf/branches/CONNECTORS-792/framework/authority-servlet/src/main/java/org/apache/manifoldcf/authorityservlet/UserACLServlet.java?rev=1535006&r1=1535005&r2=1535006&view=diff
==============================================================================
--- 
manifoldcf/branches/CONNECTORS-792/framework/authority-servlet/src/main/java/org/apache/manifoldcf/authorityservlet/UserACLServlet.java
 (original)
+++ 
manifoldcf/branches/CONNECTORS-792/framework/authority-servlet/src/main/java/org/apache/manifoldcf/authorityservlet/UserACLServlet.java
 Wed Oct 23 12:45:31 2013
@@ -106,13 +106,37 @@ public class UserACLServlet extends Http
 
       Logging.authorityService.debug("Received request");
 
+      Map<String,String> domainMap = new HashMap<String,String>();
+
+      // Legacy mode: single user name with optional domain
       String userID = request.getParameter("username");
-      if (userID == null)
+      if (userID != null)
+      {
+        String domain = request.getParameter("domain");
+        if (domain == null)
+          domain = "";
+        domainMap.put(domain,userID);
+      }
+      
+      // Now, go through enumerated username/domain pairs
+      int q = 0;
+      while (true)
+      {
+        String enumUserName = request.getParameter("username_"+q);
+        if (enumUserName == null)
+          break;
+        String enumDomain = request.getParameter("domain_"+q);
+        if (enumDomain == null)
+          enumDomain = "";
+        domainMap.put(enumDomain,enumUserName);
+      }
+      
+      if (domainMap.size() == 0)
       {
         response.sendError(response.SC_BAD_REQUEST);
         return;
       }
-
+      
       boolean idneeded = false;
       boolean aclneeded = true;
 
@@ -135,7 +159,18 @@ public class UserACLServlet extends Http
 
       if (Logging.authorityService.isDebugEnabled())
       {
-        Logging.authorityService.debug("Received authority request for user 
'"+userID+"'");
+        StringBuilder sb2 = new StringBuilder("[");
+        boolean first = true;
+        for (String domain : domainMap.keySet())
+        {
+          if (first)
+            first = false;
+          else
+            sb2.append(",");
+          
sb2.append("'").append(domain).append("':'").append(domainMap.get(domain)).append("'");
+        }
+        sb2.append("]");
+        Logging.authorityService.debug("Received authority request for 
domain:user set "+sb2.toString());
       }
 
       RequestQueue<MappingRequest> mappingQueue = 
ManifoldCF.getMappingRequestQueue();
@@ -158,15 +193,15 @@ public class UserACLServlet extends Http
       IMappingConnectionManager mappingConnManager = 
MappingConnectionManagerFactory.make(itc);
       IAuthorityConnectionManager authConnManager = 
AuthorityConnectionManagerFactory.make(itc);
 
+      // Get all mapping connections; we may not need them all but we do need 
to be able to look them all up
       IMappingConnection[] mappingConnections = 
mappingConnManager.getAllConnections();
-      IAuthorityConnection[] connections = authConnManager.getAllConnections();
       
       // One thread per connection, which is responsible for starting the 
mapping process when it is ready.
       List<MappingOrderThread> mappingThreads = new 
ArrayList<MappingOrderThread>();
       // One thread per authority, which is responsible for starting the auth 
request when it is ready.
       List<AuthOrderThread> authThreads = new ArrayList<AuthOrderThread>();
 
-      Map<String,MappingRequest> mappingRequests = new 
HashMap<String,MappingRequest>();
+      Map<MapperDescription,MappingRequest> mappingRequests = new 
HashMap<MapperDescription,MappingRequest>();
       Map<String,AuthRequest> authRequests = new HashMap<String,AuthRequest>();
 
       Map<String,IMappingConnection> mappingConnMap = new 
HashMap<String,IMappingConnection>();
@@ -178,46 +213,56 @@ public class UserACLServlet extends Http
       }
 
       // Set of connections we need to fire off
-      Set<String> activeConnections = new HashSet<String>();
+      Set<MapperDescription> activeConnections = new 
HashSet<MapperDescription>();
 
       // We do the minimal set of mapping requests and authorities.  Since it 
is the authority tokens we are
       // looking for, we start there, and build authority requests first, then 
mapping requests that support them,
       // etc.
       // Create auth requests
-      for (int i = 0; i < connections.length; i++)
+      for (String authDomain : domainMap.keySet())
       {
-        IAuthorityConnection thisConnection = connections[i];
-        String identifyingString = thisConnection.getDescription();
-        if (identifyingString == null || identifyingString.length() == 0)
-          identifyingString = thisConnection.getName();
-        
-        // Create a request
-        AuthRequest ar = new AuthRequest(
-          
thisConnection.getClassName(),identifyingString,thisConnection.getConfigParams(),thisConnection.getMaxConnections());
-        authRequests.put(thisConnection.getName(), ar);
-        
-        // We create an auth thread if there are prerequisites to meet.
-        // Otherwise, we just fire off the request
-        if (thisConnection.getPrerequisiteMapping() == null)
-        {
-          ar.setUserID(userID);
-          queue.addRequest(ar);
-        }
-        else
+        IAuthorityConnection[] connections = 
authConnManager.getDomainConnections(authDomain);
+        for (int i = 0; i < connections.length; i++)
         {
-          AuthOrderThread thread = new AuthOrderThread(identifyingString,
-            ar, thisConnection.getPrerequisiteMapping(),
-            queue, mappingRequests);
-          authThreads.add(thread);
-          activeConnections.add(thisConnection.getPrerequisiteMapping());
+          IAuthorityConnection thisConnection = connections[i];
+          String identifyingString = thisConnection.getDescription();
+          if (identifyingString == null || identifyingString.length() == 0)
+            identifyingString = thisConnection.getName();
+          
+          // Create a request
+          AuthRequest ar = new AuthRequest(
+            
thisConnection.getClassName(),identifyingString,thisConnection.getConfigParams(),thisConnection.getMaxConnections());
+          authRequests.put(thisConnection.getName(), ar);
+          
+          // We create an auth thread if there are prerequisites to meet.
+          // Otherwise, we just fire off the request
+          String domainUserID = domainMap.get(authDomain);
+          if (thisConnection.getPrerequisiteMapping() == null)
+          {
+            ar.setUserID(domainUserID);
+            queue.addRequest(ar);
+          }
+          else
+          {
+            MapperDescription md = new 
MapperDescription(thisConnection.getPrerequisiteMapping(),authDomain);
+            AuthOrderThread thread = new AuthOrderThread(identifyingString,
+              ar, md,
+              queue, mappingRequests);
+            authThreads.add(thread);
+            // The same mapper can be used for multiple domains, although this 
is likely to be uncommon.  Nevertheless,
+            // mapper invocations need to be segregated to prevent trouble
+            activeConnections.add(md);
+          }
         }
       }
 
       // Create mapping requests
       while (!activeConnections.isEmpty())
       {
-        Iterator<String> connectionIter = activeConnections.iterator();
-        String connectionName = connectionIter.next();
+        Iterator<MapperDescription> connectionIter = 
activeConnections.iterator();
+        MapperDescription mapperDesc = connectionIter.next();
+        String connectionName = mapperDesc.mapperName;
+        String authDomain = mapperDesc.authDomain;
         IMappingConnection thisConnection = mappingConnMap.get(connectionName);
         String identifyingString = thisConnection.getDescription();
         if (identifyingString == null || identifyingString.length() == 0)
@@ -226,25 +271,25 @@ public class UserACLServlet extends Http
         // Create a request
         MappingRequest mr = new MappingRequest(
           
thisConnection.getClassName(),identifyingString,thisConnection.getConfigParams(),thisConnection.getMaxConnections());
-        mappingRequests.put(connectionName, mr);
+        mappingRequests.put(mapperDesc, mr);
 
         // Either start up a thread, or just fire it off immediately.
         if (thisConnection.getPrerequisiteMapping() == null)
         {
-          mr.setUserID(userID);
+          mr.setUserID(domainMap.get(authDomain));
           mappingQueue.addRequest(mr);
         }
         else
         {
           //System.out.println("Mapper: prerequisite found: 
'"+thisConnection.getPrerequisiteMapping()+"'");
+          MapperDescription p = new 
MapperDescription(thisConnection.getPrerequisiteMapping(),authDomain);
           MappingOrderThread thread = new MappingOrderThread(identifyingString,
-            mr, thisConnection.getPrerequisiteMapping(), mappingQueue, 
mappingRequests);
+            mr, p, mappingQueue, mappingRequests);
           mappingThreads.add(thread);
-          String p = thisConnection.getPrerequisiteMapping();
           if (mappingRequests.get(p) == null)
             activeConnections.add(p);
         }
-        activeConnections.remove(connectionName);
+        activeConnections.remove(mapperDesc);
       }
       
       // Start threads.  We have to wait until all the requests have been
@@ -287,25 +332,24 @@ public class UserACLServlet extends Http
       
       // Now, work through the returning answers.
 
-      // Ask all the registered authorities for their ACLs, and merge the 
final list together.
+      // Ask all the interrogated authorities for their ACLs, and merge the 
final list together.
       StringBuilder sb = new StringBuilder();
       // Set response mime type
       response.setContentType("text/plain; charset=ISO8859-1");
       ServletOutputStream out = response.getOutputStream();
       try
       {
-        for (int i = 0; i < connections.length; i++)
+        for (String connectionName : authRequests.keySet())
         {
-          IAuthorityConnection ac = connections[i];
-          AuthRequest ar = authRequests.get(ac.getName());
+          AuthRequest ar = authRequests.get(connectionName);
 
           if (Logging.authorityService.isDebugEnabled())
-            Logging.authorityService.debug("Waiting for answer from connector 
class '"+ac.getClassName()+"' for user '"+userID+"'");
+            Logging.authorityService.debug("Waiting for answer from authority 
connection "+ar.getIdentifyingString()+" for user '"+ar.getUserID()+"'");
 
           ar.waitForComplete();
 
           if (Logging.authorityService.isDebugEnabled())
-            Logging.authorityService.debug("Received answer from connector 
class '"+ac.getClassName()+"' for user '"+userID+"'");
+            Logging.authorityService.debug("Received answer from authority 
connection "+ar.getIdentifyingString()+" for user '"+ar.getUserID()+"'");
 
           Throwable exception = ar.getAnswerException();
           AuthorizationResponse reply = ar.getAnswerResponse();
@@ -324,24 +368,24 @@ public class UserACLServlet extends Http
           if (reply == null)
           {
             if (Logging.authorityService.isDebugEnabled())
-              Logging.authorityService.debug("User '"+userID+"' mapping failed 
for authority '"+ar.getIdentifyingString()+"'");
+              Logging.authorityService.debug("User '"+ar.getUserID()+"' 
mapping failed for authority '"+ar.getIdentifyingString()+"'");
             
sb.append(USERNOTFOUND_VALUE).append(java.net.URLEncoder.encode(ar.getIdentifyingString(),"UTF-8")).append("\n");
           }
           else if (reply.getResponseStatus() == 
AuthorizationResponse.RESPONSE_UNREACHABLE)
           {
-            Logging.authorityService.warn("Authority 
'"+ar.getIdentifyingString()+"' is unreachable for user '"+userID+"'");
+            Logging.authorityService.warn("Authority 
'"+ar.getIdentifyingString()+"' is unreachable for user '"+ar.getUserID()+"'");
             
sb.append(UNREACHABLE_VALUE).append(java.net.URLEncoder.encode(ar.getIdentifyingString(),"UTF-8")).append("\n");
           }
           else if (reply.getResponseStatus() == 
AuthorizationResponse.RESPONSE_USERUNAUTHORIZED)
           {
             if (Logging.authorityService.isDebugEnabled())
-              Logging.authorityService.debug("Authority 
'"+ar.getIdentifyingString()+"' does not authorize user '"+userID+"'");
+              Logging.authorityService.debug("Authority 
'"+ar.getIdentifyingString()+"' does not authorize user '"+ar.getUserID()+"'");
             
sb.append(UNAUTHORIZED_VALUE).append(java.net.URLEncoder.encode(ar.getIdentifyingString(),"UTF-8")).append("\n");
           }
           else if (reply.getResponseStatus() == 
AuthorizationResponse.RESPONSE_USERNOTFOUND)
           {
             if (Logging.authorityService.isDebugEnabled())
-              Logging.authorityService.debug("User '"+userID+"' unknown to 
authority '"+ar.getIdentifyingString()+"'");
+              Logging.authorityService.debug("User '"+ar.getUserID()+"' 
unknown to authority '"+ar.getIdentifyingString()+"'");
             
sb.append(USERNOTFOUND_VALUE).append(java.net.URLEncoder.encode(ar.getIdentifyingString(),"UTF-8")).append("\n");
           }
           else
@@ -356,14 +400,15 @@ public class UserACLServlet extends Http
               while (j < acl.length)
               {
                 if (Logging.authorityService.isDebugEnabled())
-                  Logging.authorityService.debug("  User '"+userID+"' has Acl 
= '"+acl[j]+"' from authority '"+ar.getIdentifyingString()+"'");
-                
sb.append(TOKEN_PREFIX).append(java.net.URLEncoder.encode(ac.getName(),"UTF-8")).append(":").append(java.net.URLEncoder.encode(acl[j++],"UTF-8")).append("\n");
+                  Logging.authorityService.debug("  User '"+ar.getUserID()+"' 
has Acl = '"+acl[j]+"' from authority '"+ar.getIdentifyingString()+"'");
+                
sb.append(TOKEN_PREFIX).append(java.net.URLEncoder.encode(connectionName,"UTF-8")).append(":").append(java.net.URLEncoder.encode(acl[j++],"UTF-8")).append("\n");
               }
             }
           }
         }
 
-        if (idneeded)
+        // Maintained for backwards compatibility only; no practical use that 
I can determine here
+        if (idneeded && userID != null)
           
sb.append(ID_PREFIX).append(java.net.URLEncoder.encode(userID,"UTF-8")).append("\n");
 
         byte[] responseValue = sb.toString().getBytes("ISO8859-1");
@@ -378,7 +423,20 @@ public class UserACLServlet extends Http
       }
 
       if (Logging.authorityService.isDebugEnabled())
-        Logging.authorityService.debug("Done with request for '"+userID+"'");
+      {
+        StringBuilder sb2 = new StringBuilder("[");
+        boolean first = true;
+        for (String domain : domainMap.keySet())
+        {
+          if (first)
+            first = false;
+          else
+            sb2.append(",");
+          
sb2.append("'").append(domain).append("':'").append(domainMap.get(domain)).append("'");
+        }
+        sb2.append("]");
+        Logging.authorityService.debug("Done with request for domain:user set 
"+sb2.toString());
+      }
     }
     catch (InterruptedException e)
     {
@@ -396,6 +454,34 @@ public class UserACLServlet extends Http
     }
   }
 
+  /** This class represents a tuple of (mapper_name, auth_domain).
+  */
+  protected static class MapperDescription
+  {
+    public final String mapperName;
+    public final String authDomain;
+    
+    public MapperDescription(String mapperName, String authDomain)
+    {
+      this.mapperName = mapperName;
+      this.authDomain = authDomain;
+    }
+    
+    public int hashCode()
+    {
+      return mapperName.hashCode() + authDomain.hashCode();
+    }
+    
+    public boolean equals(Object o)
+    {
+      if (!(o instanceof MapperDescription))
+        return false;
+      MapperDescription other = (MapperDescription)o;
+      return this.mapperName.equals(other.mapperName) &&
+        this.authDomain.equals(other.authDomain);
+    }
+  }
+  
   /** This thread is responsible for making sure that the constraints for a 
given mapping connection
   * are met, and then when they are, firing off a MappingRequest.  One of 
these threads is spun up
   * for every IMappingConnection being handled.
@@ -406,8 +492,8 @@ public class UserACLServlet extends Http
   protected static class MappingOrderThread extends Thread
   {
     protected final MappingRequest request;
-    protected final String prerequisite;
-    protected final Map<String,MappingRequest> requests;
+    protected final MapperDescription prerequisite;
+    protected final Map<MapperDescription,MappingRequest> requests;
     protected final RequestQueue<MappingRequest> mappingRequestQueue;
 
     protected Throwable exception = null;
@@ -415,9 +501,9 @@ public class UserACLServlet extends Http
     public MappingOrderThread(
       String identifyingString,
       MappingRequest request,
-      String prerequisite,
+      MapperDescription prerequisite,
       RequestQueue<MappingRequest> mappingRequestQueue,
-      Map<String, MappingRequest> requests)
+      Map<MapperDescription, MappingRequest> requests)
     {
       super();
       this.request = request;
@@ -469,8 +555,8 @@ public class UserACLServlet extends Http
   protected static class AuthOrderThread extends Thread
   {
     protected final AuthRequest request;
-    protected final String prerequisite;
-    protected final Map<String,MappingRequest> mappingRequests;
+    protected final MapperDescription prerequisite;
+    protected final Map<MapperDescription,MappingRequest> mappingRequests;
     protected final RequestQueue<AuthRequest> authRequestQueue;
     
     protected Throwable exception = null;
@@ -478,9 +564,9 @@ public class UserACLServlet extends Http
     public AuthOrderThread(
       String identifyingString,
       AuthRequest request,
-      String prerequisite,
+      MapperDescription prerequisite,
       RequestQueue<AuthRequest> authRequestQueue,
-      Map<String, MappingRequest> mappingRequests)
+      Map<MapperDescription, MappingRequest> mappingRequests)
     {
       super();
       this.request = request;

Modified: 
manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/authority/AuthorityConnectionManager.java
URL: 
http://svn.apache.org/viewvc/manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/authority/AuthorityConnectionManager.java?rev=1535006&r1=1535005&r2=1535006&view=diff
==============================================================================
--- 
manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/authority/AuthorityConnectionManager.java
 (original)
+++ 
manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/authority/AuthorityConnectionManager.java
 Wed Oct 23 12:45:31 2013
@@ -213,7 +213,53 @@ public class AuthorityConnectionManager 
     }
   }
 
-  /** Obtain a list of the repository connections, ordered by name.
+  /** Obtain a list of the authority connections which correspond to an auth 
domain.
+  *@param authDomain is the domain to get connections for.
+  *@return an array of connection objects.
+  */
+  @Override
+  public IAuthorityConnection[] getDomainConnections(String authDomain)
+    throws ManifoldCFException
+  {
+    beginTransaction();
+    try
+    {
+      // Read the connections for the domain
+      StringSetBuffer ssb = new StringSetBuffer();
+      ssb.add(getAuthorityConnectionsKey());
+      StringSet localCacheKeys = new StringSet(ssb);
+      StringBuilder sb = new StringBuilder("SELECT ");
+      ArrayList list = new ArrayList();
+      sb.append(nameField).append(" FROM ").append(getTableName()).append(" 
WHERE ");
+      sb.append(buildConjunctionClause(list,new ClauseDescription[]{new 
UnitaryClause(authDomainField,authDomain)}));
+      IResultSet set = performQuery(sb.toString(),list,localCacheKeys,null);
+      String[] names = new String[set.getRowCount()];
+      int i = 0;
+      while (i < names.length)
+      {
+        IResultRow row = set.getRow(i);
+        names[i] = row.getValue(nameField).toString();
+        i++;
+      }
+      return loadMultiple(names);
+    }
+    catch (ManifoldCFException e)
+    {
+      signalRollback();
+      throw e;
+    }
+    catch (Error e)
+    {
+      signalRollback();
+      throw e;
+    }
+    finally
+    {
+      endTransaction();
+    }
+  }
+  
+  /** Obtain a list of the authority connections, ordered by name.
   *@return an array of connection objects.
   */
   @Override

Modified: 
manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/interfaces/IAuthorityConnectionManager.java
URL: 
http://svn.apache.org/viewvc/manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/interfaces/IAuthorityConnectionManager.java?rev=1535006&r1=1535005&r2=1535006&view=diff
==============================================================================
--- 
manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/interfaces/IAuthorityConnectionManager.java
 (original)
+++ 
manifoldcf/branches/CONNECTORS-792/framework/pull-agent/src/main/java/org/apache/manifoldcf/authorities/interfaces/IAuthorityConnectionManager.java
 Wed Oct 23 12:45:31 2013
@@ -51,6 +51,13 @@ public interface IAuthorityConnectionMan
   public IAuthorityConnection[] getAllConnections()
     throws ManifoldCFException;
 
+  /** Obtain a list of the authority connections which correspond to an auth 
domain.
+  *@param authDomain is the domain to get connections for.
+  *@return an array of connection objects.
+  */
+  public IAuthorityConnection[] getDomainConnections(String authDomain)
+    throws ManifoldCFException;
+
   /** Load a authority connection by name.
   *@param name is the name of the authority connection.
   *@return the loaded connection object, or null if not found.


Reply via email to