KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > mondrian > rolap > RestrictedMemberReader


1 /*
2 // $Id: //open/mondrian/src/main/mondrian/rolap/RestrictedMemberReader.java#13 $
3 // This software is subject to the terms of the Common Public License
4 // Agreement, available at the following URL:
5 // http://www.opensource.org/licenses/cpl.html.
6 // Copyright (C) 2003-2006 Julian Hyde
7 // All Rights Reserved.
8 // You must accept the terms of that agreement to use this software.
9 //
10 // jhyde, Feb 26, 2003
11 */

12 package mondrian.rolap;
13
14 import java.util.ArrayList JavaDoc;
15 import java.util.Collections JavaDoc;
16 import java.util.List JavaDoc;
17
18 import mondrian.olap.*;
19 import mondrian.rolap.sql.TupleConstraint;
20 import mondrian.rolap.sql.MemberChildrenConstraint;
21
22 /**
23  * A <code>RestrictedMemberReader</code> reads only the members of a hierarchy
24  * allowed by a role's access profile.
25  *
26  * @author jhyde
27  * @since Feb 26, 2003
28  * @version $Id: //open/mondrian/src/main/mondrian/rolap/RestrictedMemberReader.java#13 $
29  */

30 class RestrictedMemberReader extends DelegatingMemberReader {
31
32     private final Role.HierarchyAccess hierarchyAccess;
33     private final boolean ragged;
34     private final SqlConstraintFactory sqlConstraintFactory = SqlConstraintFactory.instance();
35
36     /**
37      * Creates a <code>RestrictedMemberReader</code>.
38      *
39      * <p>There's no filtering to be done unless
40      * either the role has restrictions on this hierarchy,
41      * or the hierarchy is ragged; there's a pre-condition to this effect.</p>
42      *
43      * @param memberReader Underlying (presumably unrestricted) member reader
44      * @param role Role whose access profile to obey. The role must have
45      * restrictions on this hierarchy
46      * @pre role.getAccessDetails(memberReader.getHierarchy()) != null ||
47      * memberReader.getHierarchy().isRagged()
48      */

49     RestrictedMemberReader(MemberReader memberReader, Role role) {
50         super(memberReader);
51         RolapHierarchy hierarchy = memberReader.getHierarchy();
52         hierarchyAccess = role.getAccessDetails(hierarchy);
53         ragged = hierarchy.isRagged();
54         Util.assertPrecondition(hierarchyAccess != null || ragged,
55                 "role.getAccessDetails(memberReader.getHierarchy()) != " +
56                 "null || hierarchy.isRagged()");
57     }
58
59     public boolean setCache(MemberCache cache) {
60         // Don't support cache-writeback. It would confuse the cache!
61
return false;
62     }
63
64     public RolapMember getLeadMember(RolapMember member, int n) {
65         int i = 0;
66         int increment = 1;
67         if (n < 0) {
68             increment = -1;
69             n = -n;
70         }
71         while (i < n) {
72             member = memberReader.getLeadMember(member, increment);
73             if (member.isNull()) {
74                 return member;
75             }
76             if (canSee(member)) {
77                 ++i;
78             }
79         }
80         return member;
81     }
82
83     public void getMemberChildren(
84         RolapMember parentMember,
85         List JavaDoc<RolapMember> children)
86     {
87         MemberChildrenConstraint constraint =
88             sqlConstraintFactory.getMemberChildrenConstraint(null);
89         getMemberChildren(parentMember, children, constraint);
90     }
91
92     public void getMemberChildren(
93         RolapMember parentMember,
94         List JavaDoc<RolapMember> children,
95         MemberChildrenConstraint constraint)
96     {
97         List JavaDoc<RolapMember> fullChildren = new ArrayList JavaDoc<RolapMember>();
98         memberReader.getMemberChildren(parentMember, fullChildren, constraint);
99         processMemberChildren(fullChildren, children, constraint);
100     }
101
102     private void processMemberChildren(
103         List JavaDoc<RolapMember> fullChildren,
104         List JavaDoc<RolapMember> children,
105         MemberChildrenConstraint constraint)
106     {
107         // todo: optimize if parentMember is beyond last level
108
List JavaDoc<RolapMember> grandChildren = null;
109         for (int i = 0; i < fullChildren.size(); i++) {
110             RolapMember member = fullChildren.get(i);
111             // If a child is hidden (due to raggedness) include its children.
112
// This must be done before applying access-control.
113
if (ragged) {
114                 if (member.isHidden()) {
115                     // Replace this member with all of its children.
116
// They might be hidden too, but we'll get to them in due
117
// course. They also might be access-controlled; that's why
118
// we deal with raggedness before we apply access-control.
119
fullChildren.remove(i);
120                     if (grandChildren == null) {
121                         grandChildren = new ArrayList JavaDoc<RolapMember>();
122                     } else {
123                         grandChildren.clear();
124                     }
125                     memberReader.getMemberChildren(member, grandChildren, constraint);
126                     fullChildren.addAll(i, grandChildren);
127                     // Step back to before the first child we just inserted,
128
// and go through the loop again.
129
--i;
130                     continue;
131                 }
132             }
133             // Filter out children which are invisible because of
134
// access-control.
135
if (hierarchyAccess != null) {
136                 final Access access = hierarchyAccess.getAccess(member);
137                 if (access == Access.NONE) {
138                     continue;
139                 }
140             }
141             children.add(member);
142         }
143     }
144
145     /**
146      * Writes to members which we can see.
147      * @param members Input list
148      * @param filteredMembers Output list
149      */

150     private void filterMembers(
151         List JavaDoc<RolapMember> members,
152         List JavaDoc<RolapMember> filteredMembers)
153     {
154         for (RolapMember member : members) {
155             if (canSee(member)) {
156                 filteredMembers.add(member);
157             }
158         }
159     }
160
161     private boolean canSee(final RolapMember member) {
162         if (ragged && member.isHidden()) {
163             return false;
164         }
165         if (hierarchyAccess != null) {
166             final Access access = hierarchyAccess.getAccess(member);
167             return access != Access.NONE;
168         }
169         return true;
170     }
171
172     public void getMemberChildren(List JavaDoc<RolapMember> parentMembers, List JavaDoc<RolapMember> children) {
173         MemberChildrenConstraint constraint = sqlConstraintFactory.getMemberChildrenConstraint(null);
174         getMemberChildren(parentMembers, children, constraint);
175     }
176
177     public synchronized void getMemberChildren(List JavaDoc<RolapMember> parentMembers, List JavaDoc<RolapMember> children, MemberChildrenConstraint constraint) {
178 // for (Iterator i = parentMembers.iterator(); i.hasNext();) {
179
// RolapMember parentMember = (RolapMember) i.next();
180
// getMemberChildren(parentMember, children, constraint);
181
// }
182
List JavaDoc<RolapMember> fullChildren = new ArrayList JavaDoc<RolapMember>();
183         super.getMemberChildren(parentMembers, fullChildren, constraint);
184         processMemberChildren(fullChildren, children, constraint);
185     }
186
187     public List JavaDoc<RolapMember> getMembersInLevel(RolapLevel level,
188                                   int startOrdinal,
189                                   int endOrdinal) {
190         TupleConstraint constraint = sqlConstraintFactory.getLevelMembersConstraint(null);
191         return getMembersInLevel(level, startOrdinal, endOrdinal, constraint);
192     }
193
194     public List JavaDoc<RolapMember> getMembersInLevel(RolapLevel level,
195                                 int startOrdinal,
196                                 int endOrdinal,
197                                 TupleConstraint constraint) {
198         if (hierarchyAccess != null) {
199             final int depth = level.getDepth();
200             if (hierarchyAccess.getTopLevel() != null &&
201                     depth < hierarchyAccess.getTopLevel().getDepth()) {
202                 return Collections.emptyList();
203             }
204             if (hierarchyAccess.getBottomLevel() != null &&
205                     depth > hierarchyAccess.getBottomLevel().getDepth()) {
206                 return Collections.emptyList();
207             }
208         }
209         final List JavaDoc<RolapMember> membersInLevel = super.getMembersInLevel(level,
210                 startOrdinal, endOrdinal, constraint);
211         List JavaDoc<RolapMember> filteredMembers = new ArrayList JavaDoc<RolapMember>();
212         filterMembers(membersInLevel, filteredMembers);
213         return filteredMembers;
214     }
215
216 }
217
218 // End RestrictedMemberReader.java
219
Popular Tags