View Javadoc

1   /*
2    *  Licensed to the Apache Software Foundation (ASF) under one
3    *  or more contributor license agreements.  See the NOTICE file
4    *  distributed with this work for additional information
5    *  regarding copyright ownership.  The ASF licenses this file
6    *  to you under the Apache License, Version 2.0 (the
7    *  "License"); you may not use this file except in compliance
8    *  with the License.  You may obtain a copy of the License at
9    *  
10   *    http://www.apache.org/licenses/LICENSE-2.0
11   *  
12   *  Unless required by applicable law or agreed to in writing,
13   *  software distributed under the License is distributed on an
14   *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   *  KIND, either express or implied.  See the License for the
16   *  specific language governing permissions and limitations
17   *  under the License. 
18   *  
19   */
20  package org.apache.directory.server.core.authz.support;
21  
22  
23  import java.util.Collection;
24  import java.util.Iterator;
25  
26  import javax.naming.NamingException;
27  import javax.naming.directory.Attribute;
28  
29  import org.apache.directory.server.core.entry.ServerEntry;
30  import org.apache.directory.server.core.event.Evaluator;
31  import org.apache.directory.server.core.interceptor.context.OperationContext;
32  import org.apache.directory.server.core.subtree.RefinementEvaluator;
33  import org.apache.directory.server.schema.registries.AttributeTypeRegistry;
34  import org.apache.directory.server.schema.registries.OidRegistry;
35  import org.apache.directory.server.schema.registries.Registries;
36  import org.apache.directory.shared.ldap.aci.ACITuple;
37  import org.apache.directory.shared.ldap.aci.MicroOperation;
38  import org.apache.directory.shared.ldap.aci.ProtectedItem;
39  import org.apache.directory.shared.ldap.aci.ProtectedItem.MaxValueCountItem;
40  import org.apache.directory.shared.ldap.aci.ProtectedItem.RestrictedByItem;
41  import org.apache.directory.shared.ldap.constants.AuthenticationLevel;
42  import org.apache.directory.shared.ldap.constants.SchemaConstants;
43  import org.apache.directory.shared.ldap.entry.EntryAttribute;
44  import org.apache.directory.shared.ldap.entry.Value;
45  import org.apache.directory.shared.ldap.name.LdapDN;
46  import org.apache.directory.shared.ldap.schema.AttributeType;
47  import org.apache.directory.shared.ldap.util.AttributeUtils;
48  
49  
50  /**
51   * An {@link ACITupleFilter} that discards all tuples whose {@link ProtectedItem}s
52   * are not related with the operation. (18.8.3.2, X.501)
53   *
54   * @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
55   * @version $Rev: 662440 $, $Date: 2008-06-02 16:00:23 +0200 (Mo, 02 Jun 2008) $
56   */
57  public class RelatedProtectedItemFilter implements ACITupleFilter
58  {
59      private final RefinementEvaluator refinementEvaluator;
60      private final Evaluator entryEvaluator;
61      private final OidRegistry oidRegistry;
62      private final AttributeTypeRegistry attrRegistry;
63  
64  
65      public RelatedProtectedItemFilter( RefinementEvaluator refinementEvaluator, Evaluator entryEvaluator, 
66          OidRegistry oidRegistry, AttributeTypeRegistry attrRegistry )
67      {
68          this.refinementEvaluator = refinementEvaluator;
69          this.entryEvaluator = entryEvaluator;
70          this.oidRegistry = oidRegistry;
71          this.attrRegistry = attrRegistry;
72      }
73  
74  
75      public Collection<ACITuple> filter( 
76              Registries registries, 
77              Collection<ACITuple> tuples, 
78              OperationScope scope, 
79              OperationContext opContext,
80              Collection<LdapDN> userGroupNames, 
81              LdapDN userName, 
82              ServerEntry userEntry,
83              AuthenticationLevel authenticationLevel, 
84              LdapDN entryName, 
85              String attrId,
86              Value<?> attrValue, 
87              ServerEntry entry, 
88              Collection<MicroOperation> microOperations,
89              ServerEntry entryView )
90          throws NamingException
91      {
92          if ( tuples.size() == 0 )
93          {
94              return tuples;
95          }
96  
97          for ( Iterator<ACITuple> i = tuples.iterator(); i.hasNext(); )
98          {
99              ACITuple tuple = i.next();
100             
101             if ( !isRelated( tuple, scope, userName, entryName, attrId, attrValue, entry ) )
102             {
103                 i.remove();
104             }
105         }
106 
107         return tuples;
108     }
109 
110 
111     private boolean isRelated( ACITuple tuple, OperationScope scope, LdapDN userName, LdapDN entryName, String attrId,
112                                Value<?> attrValue, ServerEntry entry ) throws NamingException, InternalError
113     {
114         String oid = null;
115         
116         if ( attrId != null )
117         {
118             oid = oidRegistry.getOid( attrId );
119         }
120         
121         for ( ProtectedItem item : tuple.getProtectedItems() )
122         {
123             if ( item == ProtectedItem.ENTRY )
124             {
125                 if ( scope == OperationScope.ENTRY )
126                 {
127                     return true;
128                 }
129             }
130             else if ( item == ProtectedItem.ALL_USER_ATTRIBUTE_TYPES )
131             {
132                 if ( scope != OperationScope.ATTRIBUTE_TYPE && scope != OperationScope.ATTRIBUTE_TYPE_AND_VALUE )
133                 {
134                     continue;
135                 }
136 
137                 return true;
138             }
139             else if ( item == ProtectedItem.ALL_USER_ATTRIBUTE_TYPES_AND_VALUES )
140             {
141                 if ( scope != OperationScope.ATTRIBUTE_TYPE && scope != OperationScope.ATTRIBUTE_TYPE_AND_VALUE )
142                 {
143                     continue;
144                 }
145 
146                 return true;
147             }
148             else if ( item instanceof ProtectedItem.AllAttributeValues )
149             {
150                 if ( scope != OperationScope.ATTRIBUTE_TYPE_AND_VALUE )
151                 {
152                     continue;
153                 }
154 
155                 ProtectedItem.AllAttributeValues aav = ( ProtectedItem.AllAttributeValues ) item;
156                 for ( Iterator<String> j = aav.iterator(); j.hasNext(); )
157                 {
158                     if ( oid.equals( oidRegistry.getOid( j.next() ) ) )
159                     {
160                         return true;
161                     }
162                 }
163             }
164             else if ( item instanceof ProtectedItem.AttributeType )
165             {
166                 if ( scope != OperationScope.ATTRIBUTE_TYPE )
167                 {
168                     continue;
169                 }
170 
171                 ProtectedItem.AttributeType at = ( ProtectedItem.AttributeType ) item;
172                 for ( Iterator<String> j = at.iterator(); j.hasNext(); )
173                 {
174                     if ( oid.equals( oidRegistry.getOid( j.next() ) ) )
175                     {
176                         return true;
177                     }
178                 }
179             }
180             else if ( item instanceof ProtectedItem.AttributeValue )
181             {
182                 if ( scope != OperationScope.ATTRIBUTE_TYPE_AND_VALUE )
183                 {
184                     continue;
185                 }
186 
187                 ProtectedItem.AttributeValue av = ( ProtectedItem.AttributeValue ) item;
188                 for ( Iterator<Attribute> j = av.iterator(); j.hasNext(); )
189                 {
190                     Attribute attr = j.next();
191                     String attrOid = oidRegistry.getOid( attr.getID() );
192                     AttributeType attrType = attrRegistry.lookup( attrOid );
193                     
194                     if ( oid.equals( attrOid ) && AttributeUtils.containsValue( attr, attrValue.get(), attrType ) )
195                     {
196                         return true;
197                     }
198                 }
199             }
200             else if ( item instanceof ProtectedItem.Classes )
201             {
202                 ProtectedItem.Classes c = ( ProtectedItem.Classes ) item;
203                 if ( refinementEvaluator.evaluate( c.getClasses(), entry.get( SchemaConstants.OBJECT_CLASS_AT ) ) )
204                 {
205                     return true;
206                 }
207             }
208             else if ( item instanceof ProtectedItem.MaxImmSub )
209             {
210                 return true;
211             }
212             else if ( item instanceof ProtectedItem.MaxValueCount )
213             {
214                 if ( scope != OperationScope.ATTRIBUTE_TYPE_AND_VALUE )
215                 {
216                     continue;
217                 }
218 
219                 ProtectedItem.MaxValueCount mvc = ( ProtectedItem.MaxValueCount ) item;
220                 for ( Iterator<MaxValueCountItem> j = mvc.iterator(); j.hasNext(); )
221                 {
222                     MaxValueCountItem mvcItem = j.next();
223                     if ( oid.equals( oidRegistry.getOid( mvcItem.getAttributeType() ) ) )
224                     {
225                         return true;
226                     }
227                 }
228             }
229             else if ( item instanceof ProtectedItem.RangeOfValues )
230             {
231                 ProtectedItem.RangeOfValues rov = ( ProtectedItem.RangeOfValues ) item;
232                 
233                 if ( entryEvaluator.evaluate( rov.getFilter(), entryName.toString(), entry ) )
234                 {
235                     return true;
236                 }
237             }
238             else if ( item instanceof ProtectedItem.RestrictedBy )
239             {
240                 if ( scope != OperationScope.ATTRIBUTE_TYPE_AND_VALUE )
241                 {
242                     continue;
243                 }
244 
245                 ProtectedItem.RestrictedBy rb = ( ProtectedItem.RestrictedBy ) item;
246                 for ( Iterator<RestrictedByItem> j = rb.iterator(); j.hasNext(); )
247                 {
248                     RestrictedByItem rbItem = j.next();
249                     if ( oid.equals( oidRegistry.getOid( rbItem.getAttributeType() ) ) )
250                     {
251                         return true;
252                     }
253                 }
254             }
255             else if ( item instanceof ProtectedItem.SelfValue )
256             {
257                 if ( scope != OperationScope.ATTRIBUTE_TYPE_AND_VALUE && scope != OperationScope.ATTRIBUTE_TYPE )
258                 {
259                     continue;
260                 }
261 
262                 ProtectedItem.SelfValue sv = ( ProtectedItem.SelfValue ) item;
263                 for ( Iterator<String> j = sv.iterator(); j.hasNext(); )
264                 {
265                     String svItem = j.next();
266                     if ( oid.equals( oidRegistry.getOid( svItem ) ) )
267                     {
268                         EntryAttribute attr = entry.get( oid );
269                         
270                         if ( ( attr != null ) && 
271                              ( ( attr.contains( userName.toNormName() ) || 
272                                ( attr.contains( userName.getUpName() ) ) ) ) )
273                         {
274                             return true;
275                         }
276                     }
277                 }
278             }
279             else
280             {
281                 throw new InternalError( "Unexpected protectedItem: " + item.getClass().getName() );
282             }
283         }
284 
285         return false;
286     }
287 }