View Javadoc
1   /**
2    * Waffle (https://github.com/dblock/waffle)
3    *
4    * Copyright (c) 2010 - 2015 Application Security, Inc.
5    *
6    * All rights reserved. This program and the accompanying materials
7    * are made available under the terms of the Eclipse Public License v1.0
8    * which accompanies this distribution, and is available at
9    * http://www.eclipse.org/legal/epl-v10.html
10   *
11   * Contributors:
12   *     Application Security, Inc.
13   */
14  package waffle.apache;
15  
16  import java.util.ArrayList;
17  import java.util.HashMap;
18  import java.util.List;
19  import java.util.Map;
20  
21  import org.apache.catalina.realm.GenericPrincipal;
22  
23  import com.google.common.base.Joiner;
24  
25  import waffle.windows.auth.IWindowsAccount;
26  import waffle.windows.auth.IWindowsIdentity;
27  import waffle.windows.auth.PrincipalFormat;
28  import waffle.windows.auth.WindowsAccount;
29  
30  /**
31   * A Windows Principal.
32   * 
33   * @author dblock[at]dblock[dot]org
34   */
35  public class GenericWindowsPrincipal extends GenericPrincipal {
36  
37      private static final long serialVersionUID = 1L;
38  
39      /** The sid. */
40      private final byte[]                      sid;
41  
42      /** The sid string. */
43      private final String                      sidString;
44  
45      /** The groups. */
46      private final Map<String, WindowsAccount> groups;
47  
48      /**
49       * A windows principal.
50       * 
51       * @param windowsIdentity
52       *            Windows identity.
53       * @param principalFormat
54       *            Principal format.
55       * @param roleFormat
56       *            Role format.
57       */
58      public GenericWindowsPrincipal(final IWindowsIdentity windowsIdentity, final PrincipalFormat principalFormat,
59              final PrincipalFormat roleFormat) {
60          super(windowsIdentity.getFqn(), "", GenericWindowsPrincipal.getRoles(windowsIdentity, principalFormat, roleFormat));
61          this.sid = windowsIdentity.getSid();
62          this.sidString = windowsIdentity.getSidString();
63          this.groups = GenericWindowsPrincipal.getGroups(windowsIdentity.getGroups());
64      }
65  
66      /**
67       * Gets the roles.
68       *
69       * @param windowsIdentity
70       *            the windows identity
71       * @param principalFormat
72       *            the principal format
73       * @param roleFormat
74       *            the role format
75       * @return the roles
76       */
77      private static List<String> getRoles(final IWindowsIdentity windowsIdentity, final PrincipalFormat principalFormat,
78              final PrincipalFormat roleFormat) {
79          final List<String> roles = new ArrayList<String>();
80          roles.addAll(GenericWindowsPrincipal.getPrincipalNames(windowsIdentity, principalFormat));
81          for (final IWindowsAccount group : windowsIdentity.getGroups()) {
82              roles.addAll(GenericWindowsPrincipal.getRoleNames(group, roleFormat));
83          }
84          return roles;
85      }
86  
87      /**
88       * Gets the groups.
89       *
90       * @param groups
91       *            the groups
92       * @return the groups
93       */
94      private static Map<String, WindowsAccount> getGroups(final IWindowsAccount[] groups) {
95          final Map<String, WindowsAccount> groupMap = new HashMap<String, WindowsAccount>();
96          for (final IWindowsAccount group : groups) {
97              groupMap.put(group.getFqn(), new WindowsAccount(group));
98          }
99          return groupMap;
100     }
101 
102     /**
103      * Byte representation of the SID.
104      * 
105      * @return Array of bytes.
106      */
107     public byte[] getSid() {
108         return this.sid.clone();
109     }
110 
111     /**
112      * String representation of the SID.
113      * 
114      * @return String.
115      */
116     public String getSidString() {
117         return this.sidString;
118     }
119 
120     /**
121      * Windows groups that the user is a member of.
122      * 
123      * @return A map of group names to groups.
124      */
125     public Map<String, WindowsAccount> getGroups() {
126         return this.groups;
127     }
128 
129     /**
130      * Returns a list of role principal objects.
131      * 
132      * @param group
133      *            Windows group.
134      * @param principalFormat
135      *            Principal format.
136      * @return List of role principal objects.
137      */
138     private static List<String> getRoleNames(final IWindowsAccount group, final PrincipalFormat principalFormat) {
139         final List<String> principals = new ArrayList<String>();
140         switch (principalFormat) {
141             case FQN:
142                 principals.add(group.getFqn());
143                 break;
144             case SID:
145                 principals.add(group.getSidString());
146                 break;
147             case BOTH:
148                 principals.add(group.getFqn());
149                 principals.add(group.getSidString());
150                 break;
151             case NONE:
152                 break;
153             default:
154                 break;
155         }
156         return principals;
157     }
158 
159     /**
160      * Returns a list of user principal objects.
161      * 
162      * @param windowsIdentity
163      *            Windows identity.
164      * @param principalFormat
165      *            Principal format.
166      * @return A list of user principal objects.
167      */
168     private static List<String> getPrincipalNames(final IWindowsIdentity windowsIdentity,
169             final PrincipalFormat principalFormat) {
170         final List<String> principals = new ArrayList<String>();
171         switch (principalFormat) {
172             case FQN:
173                 principals.add(windowsIdentity.getFqn());
174                 break;
175             case SID:
176                 principals.add(windowsIdentity.getSidString());
177                 break;
178             case BOTH:
179                 principals.add(windowsIdentity.getFqn());
180                 principals.add(windowsIdentity.getSidString());
181                 break;
182             case NONE:
183                 break;
184             default:
185                 break;
186         }
187         return principals;
188     }
189 
190     /**
191      * Get an array of roles as a string.
192      * 
193      * @return Role1, Role2, ...
194      */
195     public String getRolesString() {
196         return Joiner.on(", ").join(this.getRoles());
197     }
198 }