Coverage Report - org.apache.shiro.subject.Subject
 
Classes in this File Line Coverage Branch Coverage Complexity
Subject
N/A
N/A
1.25
Subject$Builder
29%
11/37
12%
2/16
1.25
 
 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  
 package org.apache.shiro.subject;
 20  
 
 21  
 import org.apache.shiro.SecurityUtils;
 22  
 import org.apache.shiro.authc.AuthenticationException;
 23  
 import org.apache.shiro.authc.AuthenticationToken;
 24  
 import org.apache.shiro.authz.AuthorizationException;
 25  
 import org.apache.shiro.authz.Permission;
 26  
 import org.apache.shiro.mgt.SecurityManager;
 27  
 import org.apache.shiro.mgt.SubjectFactory;
 28  
 import org.apache.shiro.session.Session;
 29  
 import org.apache.shiro.subject.support.DefaultSubjectContext;
 30  
 import org.apache.shiro.util.CollectionUtils;
 31  
 import org.apache.shiro.util.StringUtils;
 32  
 
 33  
 import java.io.Serializable;
 34  
 import java.util.Collection;
 35  
 import java.util.List;
 36  
 import java.util.concurrent.Callable;
 37  
 
 38  
 /**
 39  
  * A {@code Subject} represents state and security operations for a <em>single</em> application user.
 40  
  * These operations include authentication (login/logout), authorization (access control), and
 41  
  * session access. It is Shiro's primary mechanism for single-user security functionality.
 42  
  * <h3>Acquiring a Subject</h3>
 43  
  * To acquire the currently-executing {@code Subject}, application developers will almost always use
 44  
  * {@code SecurityUtils}:
 45  
  * <pre>
 46  
  * {@link SecurityUtils SecurityUtils}.{@link org.apache.shiro.SecurityUtils#getSubject() getSubject()}</pre>
 47  
  * Almost all security operations should be performed with the {@code Subject} returned from this method.
 48  
  * <h3>Permission methods</h3>
 49  
  * Note that there are many *Permission methods in this interface overloaded to accept String arguments instead of
 50  
  * {@link Permission Permission} instances. They are a convenience allowing the caller to use a String representation of
 51  
  * a {@link Permission Permission} if desired.  The underlying Authorization subsystem implementations will usually
 52  
  * simply convert these String values to {@link Permission Permission} instances and then just call the corresponding
 53  
  * type-safe method.  (Shiro's default implementations do String-to-Permission conversion for these methods using
 54  
  * {@link org.apache.shiro.authz.permission.PermissionResolver PermissionResolver}s.)
 55  
  * <p/>
 56  
  * These overloaded *Permission methods forgo type-saftey for the benefit of convenience and simplicity,
 57  
  * so you should choose which ones to use based on your preferences and needs.
 58  
  *
 59  
  * @since 0.1
 60  
  */
 61  
 public interface Subject {
 62  
 
 63  
     /**
 64  
      * Returns this Subject's application-wide uniquely identifying principal, or {@code null} if this
 65  
      * Subject is anonymous because it doesn't yet have any associated account data (for example,
 66  
      * if they haven't logged in).
 67  
      * <p/>
 68  
      * The term <em>principal</em> is just a fancy security term for any identifying attribute(s) of an application
 69  
      * user, such as a username, or user id, or public key, or anything else you might use in your application to
 70  
      * identify a user.
 71  
      * <h4>Uniqueness</h4>
 72  
      * Although given names and family names (first/last) are technically considered principals as well,
 73  
      * Shiro expects the object returned from this method to be an identifying attribute unique across
 74  
      * your entire application.
 75  
      * <p/>
 76  
      * This implies that things like given names and family names are usually poor
 77  
      * candidates as return values since they are rarely guaranteed to be unique;  Things often used for this value:
 78  
      * <ul>
 79  
      * <li>A {@code long} RDBMS surrogate primary key</li>
 80  
      * <li>An application-unique username</li>
 81  
      * <li>A {@link java.util.UUID UUID}</li>
 82  
      * <li>An LDAP Unique ID</li>
 83  
      * </ul>
 84  
      * or any other similar suitable unique mechanism valuable to your application.
 85  
      * <p/>
 86  
      * Most implementations will simply return
 87  
      * <code>{@link #getPrincipals()}.{@link org.apache.shiro.subject.PrincipalCollection#getPrimaryPrincipal() getPrimaryPrincipal()}</code>
 88  
      *
 89  
      * @return this Subject's application-specific unique identity.
 90  
      * @see org.apache.shiro.subject.PrincipalCollection#getPrimaryPrincipal()
 91  
      */
 92  
     Object getPrincipal();
 93  
 
 94  
     /**
 95  
      * Returns this Subject's principals (identifying attributes) in the form of a {@code PrincipalCollection} or
 96  
      * {@code null} if this Subject is anonymous because it doesn't yet have any associated account data (for example,
 97  
      * if they haven't logged in).
 98  
      * <p/>
 99  
      * The word &quot;principals&quot; is nothing more than a fancy security term for identifying attributes associated
 100  
      * with a Subject, aka, application user.  For example, user id, a surname (family/last name), given (first) name,
 101  
      * social security number, nickname, username, etc, are all examples of a principal.
 102  
      *
 103  
      * @return all of this Subject's principals (identifying attributes).
 104  
      * @see #getPrincipal()
 105  
      * @see org.apache.shiro.subject.PrincipalCollection#getPrimaryPrincipal()
 106  
      */
 107  
     PrincipalCollection getPrincipals();
 108  
 
 109  
     /**
 110  
      * Returns {@code true} if this Subject is permitted to perform an action or access a resource summarized by the
 111  
      * specified permission string.
 112  
      * <p/>
 113  
      * This is an overloaded method for the corresponding type-safe {@link Permission Permission} variant.
 114  
      * Please see the class-level JavaDoc for more information on these String-based permission methods.
 115  
      *
 116  
      * @param permission the String representation of a Permission that is being checked.
 117  
      * @return true if this Subject is permitted, false otherwise.
 118  
      * @see #isPermitted(Permission permission)
 119  
      * @since 0.9
 120  
      */
 121  
     boolean isPermitted(String permission);
 122  
 
 123  
     /**
 124  
      * Returns {@code true} if this Subject is permitted to perform an action or access a resource summarized by the
 125  
      * specified permission.
 126  
      * <p/>
 127  
      * More specifically, this method determines if any {@code Permission}s associated
 128  
      * with the subject {@link Permission#implies(Permission) imply} the specified permission.
 129  
      *
 130  
      * @param permission the permission that is being checked.
 131  
      * @return true if this Subject is permitted, false otherwise.
 132  
      */
 133  
     boolean isPermitted(Permission permission);
 134  
 
 135  
     /**
 136  
      * Checks if this Subject implies the given permission strings and returns a boolean array indicating which
 137  
      * permissions are implied.
 138  
      * <p/>
 139  
      * This is an overloaded method for the corresponding type-safe {@link Permission Permission} variant.
 140  
      * Please see the class-level JavaDoc for more information on these String-based permission methods.
 141  
      *
 142  
      * @param permissions the String representations of the Permissions that are being checked.
 143  
      * @return a boolean array where indices correspond to the index of the
 144  
      *         permissions in the given list.  A true value at an index indicates this Subject is permitted for
 145  
      *         for the associated {@code Permission} string in the list.  A false value at an index
 146  
      *         indicates otherwise.
 147  
      * @since 0.9
 148  
      */
 149  
     boolean[] isPermitted(String... permissions);
 150  
 
 151  
     /**
 152  
      * Checks if this Subject implies the given Permissions and returns a boolean array indicating which permissions
 153  
      * are implied.
 154  
      * <p/>
 155  
      * More specifically, this method should determine if each {@code Permission} in
 156  
      * the array is {@link Permission#implies(Permission) implied} by permissions
 157  
      * already associated with the subject.
 158  
      * <p/>
 159  
      * This is primarily a performance-enhancing method to help reduce the number of
 160  
      * {@link #isPermitted} invocations over the wire in client/server systems.
 161  
      *
 162  
      * @param permissions the permissions that are being checked.
 163  
      * @return a boolean array where indices correspond to the index of the
 164  
      *         permissions in the given list.  A true value at an index indicates this Subject is permitted for
 165  
      *         for the associated {@code Permission} object in the list.  A false value at an index
 166  
      *         indicates otherwise.
 167  
      */
 168  
     boolean[] isPermitted(List<Permission> permissions);
 169  
 
 170  
     /**
 171  
      * Returns {@code true} if this Subject implies all of the specified permission strings, {@code false} otherwise.
 172  
      * <p/>
 173  
      * This is an overloaded method for the corresponding type-safe {@link org.apache.shiro.authz.Permission Permission}
 174  
      * variant.  Please see the class-level JavaDoc for more information on these String-based permission methods.
 175  
      *
 176  
      * @param permissions the String representations of the Permissions that are being checked.
 177  
      * @return true if this Subject has all of the specified permissions, false otherwise.
 178  
      * @see #isPermittedAll(Collection)
 179  
      * @since 0.9
 180  
      */
 181  
     boolean isPermittedAll(String... permissions);
 182  
 
 183  
     /**
 184  
      * Returns {@code true} if this Subject implies all of the specified permissions, {@code false} otherwise.
 185  
      * <p/>
 186  
      * More specifically, this method determines if all of the given {@code Permission}s are
 187  
      * {@link Permission#implies(Permission) implied by} permissions already associated with this Subject.
 188  
      *
 189  
      * @param permissions the permissions to check.
 190  
      * @return true if this Subject has all of the specified permissions, false otherwise.
 191  
      */
 192  
     boolean isPermittedAll(Collection<Permission> permissions);
 193  
 
 194  
     /**
 195  
      * Ensures this Subject implies the specified permission String.
 196  
      * <p/>
 197  
      * If this subject's existing associated permissions do not {@link Permission#implies(Permission)} imply}
 198  
      * the given permission, an {@link org.apache.shiro.authz.AuthorizationException} will be thrown.
 199  
      * <p/>
 200  
      * This is an overloaded method for the corresponding type-safe {@link Permission Permission} variant.
 201  
      * Please see the class-level JavaDoc for more information on these String-based permission methods.
 202  
      *
 203  
      * @param permission the String representation of the Permission to check.
 204  
      * @throws org.apache.shiro.authz.AuthorizationException
 205  
      *          if the user does not have the permission.
 206  
      * @since 0.9
 207  
      */
 208  
     void checkPermission(String permission) throws AuthorizationException;
 209  
 
 210  
     /**
 211  
      * Ensures this Subject {@link Permission#implies(Permission) implies} the specified {@code Permission}.
 212  
      * <p/>
 213  
      * If this subject's existing associated permissions do not {@link Permission#implies(Permission) imply}
 214  
      * the given permission, an {@link org.apache.shiro.authz.AuthorizationException} will be thrown.
 215  
      *
 216  
      * @param permission the Permission to check.
 217  
      * @throws org.apache.shiro.authz.AuthorizationException
 218  
      *          if this Subject does not have the permission.
 219  
      */
 220  
     void checkPermission(Permission permission) throws AuthorizationException;
 221  
 
 222  
     /**
 223  
      * Ensures this Subject
 224  
      * {@link org.apache.shiro.authz.Permission#implies(org.apache.shiro.authz.Permission) implies} all of the
 225  
      * specified permission strings.
 226  
      * <p/>
 227  
      * If this subject's existing associated permissions do not
 228  
      * {@link org.apache.shiro.authz.Permission#implies(org.apache.shiro.authz.Permission) imply} all of the given permissions,
 229  
      * an {@link org.apache.shiro.authz.AuthorizationException} will be thrown.
 230  
      * <p/>
 231  
      * This is an overloaded method for the corresponding type-safe {@link Permission Permission} variant.
 232  
      * Please see the class-level JavaDoc for more information on these String-based permission methods.
 233  
      *
 234  
      * @param permissions the string representations of Permissions to check.
 235  
      * @throws AuthorizationException if this Subject does not have all of the given permissions.
 236  
      * @since 0.9
 237  
      */
 238  
     void checkPermissions(String... permissions) throws AuthorizationException;
 239  
 
 240  
     /**
 241  
      * Ensures this Subject
 242  
      * {@link org.apache.shiro.authz.Permission#implies(org.apache.shiro.authz.Permission) implies} all of the
 243  
      * specified permission strings.
 244  
      * <p/>
 245  
      * If this subject's existing associated permissions do not
 246  
      * {@link org.apache.shiro.authz.Permission#implies(org.apache.shiro.authz.Permission) imply} all of the given permissions,
 247  
      * an {@link org.apache.shiro.authz.AuthorizationException} will be thrown.
 248  
      *
 249  
      * @param permissions the Permissions to check.
 250  
      * @throws AuthorizationException if this Subject does not have all of the given permissions.
 251  
      */
 252  
     void checkPermissions(Collection<Permission> permissions) throws AuthorizationException;
 253  
 
 254  
     /**
 255  
      * Returns {@code true} if this Subject has the specified role, {@code false} otherwise.
 256  
      *
 257  
      * @param roleIdentifier the application-specific role identifier (usually a role id or role name).
 258  
      * @return {@code true} if this Subject has the specified role, {@code false} otherwise.
 259  
      */
 260  
     boolean hasRole(String roleIdentifier);
 261  
 
 262  
     /**
 263  
      * Checks if this Subject has the specified roles, returning a boolean array indicating
 264  
      * which roles are associated.
 265  
      * <p/>
 266  
      * This is primarily a performance-enhancing method to help reduce the number of
 267  
      * {@link #hasRole} invocations over the wire in client/server systems.
 268  
      *
 269  
      * @param roleIdentifiers the application-specific role identifiers to check (usually role ids or role names).
 270  
      * @return a boolean array where indices correspond to the index of the
 271  
      *         roles in the given identifiers.  A true value indicates this Subject has the
 272  
      *         role at that index.  False indicates this Subject does not have the role at that index.
 273  
      */
 274  
     boolean[] hasRoles(List<String> roleIdentifiers);
 275  
 
 276  
     /**
 277  
      * Returns {@code true} if this Subject has all of the specified roles, {@code false} otherwise.
 278  
      *
 279  
      * @param roleIdentifiers the application-specific role identifiers to check (usually role ids or role names).
 280  
      * @return true if this Subject has all the roles, false otherwise.
 281  
      */
 282  
     boolean hasAllRoles(Collection<String> roleIdentifiers);
 283  
 
 284  
     /**
 285  
      * Asserts this Subject has the specified role by returning quietly if they do or throwing an
 286  
      * {@link org.apache.shiro.authz.AuthorizationException} if they do not.
 287  
      *
 288  
      * @param roleIdentifier the application-specific role identifier (usually a role id or role name ).
 289  
      * @throws org.apache.shiro.authz.AuthorizationException
 290  
      *          if this Subject does not have the role.
 291  
      */
 292  
     void checkRole(String roleIdentifier) throws AuthorizationException;
 293  
 
 294  
     /**
 295  
      * Asserts this Subject has all of the specified roles by returning quietly if they do or throwing an
 296  
      * {@link org.apache.shiro.authz.AuthorizationException} if they do not.
 297  
      *
 298  
      * @param roleIdentifiers the application-specific role identifiers to check (usually role ids or role names).
 299  
      * @throws org.apache.shiro.authz.AuthorizationException
 300  
      *          if this Subject does not have all of the specified roles.
 301  
      */
 302  
     void checkRoles(Collection<String> roleIdentifiers) throws AuthorizationException;
 303  
 
 304  
     /**
 305  
      * Same as {@link #checkRoles(Collection<String> roleIdentifiers) checkRoles(Collection<String> roleIdentifiers)} but
 306  
      * doesn't require a collection as a an argument.
 307  
      * Asserts this Subject has all of the specified roles by returning quietly if they do or throwing an
 308  
      * {@link org.apache.shiro.authz.AuthorizationException} if they do not.
 309  
      *
 310  
      * @param roleIdentifiers roleIdentifiers the application-specific role identifiers to check (usually role ids or role names).
 311  
      * @throws AuthorizationException org.apache.shiro.authz.AuthorizationException
 312  
      *          if this Subject does not have all of the specified roles.
 313  
      * @since 1.1.0
 314  
      */
 315  
     void checkRoles(String... roleIdentifiers) throws AuthorizationException;
 316  
 
 317  
     /**
 318  
      * Performs a login attempt for this Subject/user.  If unsuccessful,
 319  
      * an {@link AuthenticationException} is thrown, the subclass of which identifies why the attempt failed.
 320  
      * If successful, the account data associated with the submitted principals/credentials will be
 321  
      * associated with this {@code Subject} and the method will return quietly.
 322  
      * <p/>
 323  
      * Upon returning quietly, this {@code Subject} instance can be considered
 324  
      * authenticated and {@link #getPrincipal() getPrincipal()} will be non-null and
 325  
      * {@link #isAuthenticated() isAuthenticated()} will be {@code true}.
 326  
      *
 327  
      * @param token the token encapsulating the subject's principals and credentials to be passed to the
 328  
      *              Authentication subsystem for verification.
 329  
      * @throws org.apache.shiro.authc.AuthenticationException
 330  
      *          if the authentication attempt fails.
 331  
      * @since 0.9
 332  
      */
 333  
     void login(AuthenticationToken token) throws AuthenticationException;
 334  
 
 335  
     /**
 336  
      * Returns {@code true} if this Subject/user proved their identity <em>during their current session</em>
 337  
      * by providing valid credentials matching those known to the system, {@code false} otherwise.
 338  
      * <p/>
 339  
      * Note that even if this Subject's identity has been remembered via 'remember me' services, this method will
 340  
      * still return {@code false} unless the user has actually logged in with proper credentials <em>during their
 341  
      * current session</em>.  See the {@link #isRemembered() isRemembered()} method JavaDoc for more.
 342  
      *
 343  
      * @return {@code true} if this Subject proved their identity during their current session
 344  
      *         by providing valid credentials matching those known to the system, {@code false} otherwise.
 345  
      * @since 0.9
 346  
      */
 347  
     boolean isAuthenticated();
 348  
 
 349  
 
 350  
     /**
 351  
      * Returns {@code true} if this {@code Subject} has an identity (it is not anonymous) and the identity
 352  
      * (aka {@link #getPrincipals() principals}) is remembered from a successful authentication during a previous
 353  
      * session.
 354  
      * <p/>
 355  
      * Although the underlying implementation determines exactly how this method functions, most implementations have
 356  
      * this method act as the logical equivalent to this code:
 357  
      * <pre>
 358  
      * {@link #getPrincipal() getPrincipal()} != null && !{@link #isAuthenticated() isAuthenticated()}</pre>
 359  
      * <p/>
 360  
      * Note as indicated by the above code example, if a {@code Subject} is remembered, they are
 361  
      * <em>NOT</em> considered authenticated.  A check against {@link #isAuthenticated() isAuthenticated()} is a more
 362  
      * strict check than that reflected by this method.  For example, a check to see if a subject can access financial
 363  
      * information should almost always depend on {@link #isAuthenticated() isAuthenticated()} to <em>guarantee</em> a
 364  
      * verified identity, and not this method.
 365  
      * <p/>
 366  
      * Once the subject is authenticated, they are no longer considered only remembered because their identity would
 367  
      * have been verified during the current session.
 368  
      * <h4>Remembered vs Authenticated</h4>
 369  
      * Authentication is the process of <em>proving</em> you are who you say you are.  When a user is only remembered,
 370  
      * the remembered identity gives the system an idea who that user probably is, but in reality, has no way of
 371  
      * absolutely <em>guaranteeing</em> if the remembered {@code Subject} represents the user currently
 372  
      * using the application.
 373  
      * <p/>
 374  
      * So although many parts of the application can still perform user-specific logic based on the remembered
 375  
      * {@link #getPrincipals() principals}, such as customized views, it should never perform highly-sensitive
 376  
      * operations until the user has legitimately verified their identity by executing a successful authentication
 377  
      * attempt.
 378  
      * <p/>
 379  
      * We see this paradigm all over the web, and we will use <a href="http://www.amazon.com">Amazon.com</a> as an
 380  
      * example:
 381  
      * <p/>
 382  
      * When you visit Amazon.com and perform a login and ask it to 'remember me', it will set a cookie with your
 383  
      * identity.  If you don't log out and your session expires, and you come back, say the next day, Amazon still knows
 384  
      * who you <em>probably</em> are: you still see all of your book and movie recommendations and similar user-specific
 385  
      * features since these are based on your (remembered) user id.
 386  
      * <p/>
 387  
      * BUT, if you try to do something sensitive, such as access your account's billing data, Amazon forces you
 388  
      * to do an actual log-in, requiring your username and password.
 389  
      * <p/>
 390  
      * This is because although amazon.com assumed your identity from 'remember me', it recognized that you were not
 391  
      * actually authenticated.  The only way to really guarantee you are who you say you are, and therefore allow you
 392  
      * access to sensitive account data, is to force you to perform an actual successful authentication.  You can
 393  
      * check this guarantee via the {@link #isAuthenticated() isAuthenticated()} method and not via this method.
 394  
      *
 395  
      * @return {@code true} if this {@code Subject}'s identity (aka {@link #getPrincipals() principals}) is
 396  
      *         remembered from a successful authentication during a previous session, {@code false} otherwise.
 397  
      * @since 1.0
 398  
      */
 399  
     boolean isRemembered();
 400  
 
 401  
     /**
 402  
      * Returns the application {@code Session} associated with this Subject.  If no session exists when this
 403  
      * method is called, a new session will be created, associated with this Subject, and then returned.
 404  
      *
 405  
      * @return the application {@code Session} associated with this Subject.
 406  
      * @see #getSession(boolean)
 407  
      * @since 0.2
 408  
      */
 409  
     Session getSession();
 410  
 
 411  
     /**
 412  
      * Returns the application {@code Session} associated with this Subject.  Based on the boolean argument,
 413  
      * this method functions as follows:
 414  
      * <ul>
 415  
      * <li>If there is already an existing session associated with this {@code Subject}, it is returned and
 416  
      * the {@code create} argument is ignored.</li>
 417  
      * <li>If no session exists and {@code create} is {@code true}, a new session will be created, associated with
 418  
      * this {@code Subject} and then returned.</li>
 419  
      * <li>If no session exists and {@code create} is {@code false}, {@code null} is returned.</li>
 420  
      * </ul>
 421  
      *
 422  
      * @param create boolean argument determining if a new session should be created or not if there is no existing session.
 423  
      * @return the application {@code Session} associated with this {@code Subject} or {@code null} based
 424  
      *         on the above described logic.
 425  
      * @since 0.2
 426  
      */
 427  
     Session getSession(boolean create);
 428  
 
 429  
     /**
 430  
      * Logs out this Subject and invalidates and/or removes any associated entities,
 431  
      * such as a {@link Session Session} and authorization data.  After this method is called, the Subject is
 432  
      * considered 'anonymous' and may continue to be used for another log-in if desired.
 433  
      * <h3>Web Environment Warning</h3>
 434  
      * Calling this method in web environments will usually remove any associated session cookie as part of
 435  
      * session invalidation.  Because cookies are part of the HTTP header, and headers can only be set before the
 436  
      * response body (html, image, etc) is sent, this method in web environments must be called before <em>any</em>
 437  
      * content has been rendered.
 438  
      * <p/>
 439  
      * The typical approach most applications use in this scenario is to redirect the user to a different
 440  
      * location (e.g. home page) immediately after calling this method.  This is an effect of the HTTP protocol
 441  
      * itself and not a reflection of Shiro's implementation.
 442  
      * <p/>
 443  
      * Non-HTTP environments may of course use a logged-out subject for login again if desired.
 444  
      */
 445  
     void logout();
 446  
 
 447  
     /**
 448  
      * Associates the specified {@code Callable} with this {@code Subject} instance and then executes it on the
 449  
      * currently running thread.  If you want to execute the {@code Callable} on a different thread, it is better to
 450  
      * use the {@link #associateWith(Callable)} method instead.
 451  
      *
 452  
      * @param callable the Callable to associate with this subject and then execute.
 453  
      * @param <V>      the type of return value the {@code Callable} will return
 454  
      * @return the resulting object returned by the {@code Callable}'s execution.
 455  
      * @throws ExecutionException if the {@code Callable}'s {@link Callable#call call} method throws an exception.
 456  
      * @since 1.0
 457  
      */
 458  
     <V> V execute(Callable<V> callable) throws ExecutionException;
 459  
 
 460  
     /**
 461  
      * Associates the specified {@code Runnable} with this {@code Subject} instance and then executes it on the
 462  
      * currently running thread.  If you want to execute the {@code Runnable} on a different thread, it is better to
 463  
      * use the {@link #associateWith(Runnable)} method instead.
 464  
      * <p/>
 465  
      * <b>Note</b>: This method is primarily provided to execute existing/legacy Runnable implementations.  It is better
 466  
      * for new code to use {@link #execute(Callable)} since that supports the ability to return values and catch
 467  
      * exceptions.
 468  
      *
 469  
      * @param runnable the {@code Runnable} to associate with this {@code Subject} and then execute.
 470  
      * @since 1.0
 471  
      */
 472  
     void execute(Runnable runnable);
 473  
 
 474  
     /**
 475  
      * Returns a {@code Callable} instance matching the given argument while additionally ensuring that it will
 476  
      * retain and execute under this Subject's identity.  The returned object can be used with an
 477  
      * {@link java.util.concurrent.ExecutorService ExecutorService} to execute as this Subject.
 478  
      * <p/>
 479  
      * This will effectively ensure that any calls to
 480  
      * {@code SecurityUtils}.{@link SecurityUtils#getSubject() getSubject()} and related functionality will continue
 481  
      * to function properly on any thread that executes the returned {@code Callable} instance.
 482  
      *
 483  
      * @param callable the callable to execute as this {@code Subject}
 484  
      * @param <V>      the {@code Callable}s return value type
 485  
      * @return a {@code Callable} that can be run as this {@code Subject}.
 486  
      * @since 1.0
 487  
      */
 488  
     <V> Callable<V> associateWith(Callable<V> callable);
 489  
 
 490  
     /**
 491  
      * Returns a {@code Runnable} instance matching the given argument while additionally ensuring that it will
 492  
      * retain and execute under this Subject's identity.  The returned object can be used with an
 493  
      * {@link java.util.concurrent.Executor Executor} or another thread to execute as this Subject.
 494  
      * <p/>
 495  
      * This will effectively ensure that any calls to
 496  
      * {@code SecurityUtils}.{@link SecurityUtils#getSubject() getSubject()} and related functionality will continue
 497  
      * to function properly on any thread that executes the returned {@code Runnable} instance.
 498  
      * <p/>
 499  
      * *Note that if you need a return value to be returned as a result of the runnable's execution or if you need to
 500  
      * react to any Exceptions, it is highly recommended to use the
 501  
      * {@link #associateWith(java.util.concurrent.Callable) createCallable} method instead of this one.
 502  
      *
 503  
      * @param runnable the runnable to execute as this {@code Subject}
 504  
      * @return a {@code Runnable} that can be run as this {@code Subject} on another thread.
 505  
      * @see #associateWith (java.util.concurrent.Callable)
 506  
      * @since 1.0
 507  
      */
 508  
     Runnable associateWith(Runnable runnable);
 509  
 
 510  
     /**
 511  
      * Allows this subject to 'run as' or 'assume' another identity indefinitely.  This can only be
 512  
      * called when the {@code Subject} instance already has an identity (i.e. they are remembered from a previous
 513  
      * log-in or they have authenticated during their current session).
 514  
      * <p/>
 515  
      * Some notes about {@code runAs}:
 516  
      * <ul>
 517  
      * <li>You can tell if a {@code Subject} is 'running as' another identity by calling the
 518  
      * {@link #isRunAs() isRunAs()} method.</li>
 519  
      * <li>If running as another identity, you can determine what the previous 'pre run as' identity
 520  
      * was by calling the {@link #getPreviousPrincipals() getPreviousPrincipals()} method.</li>
 521  
      * <li>When you want a {@code Subject} to stop running as another identity, you can return to its previous
 522  
      * 'pre run as' identity by calling the {@link #releaseRunAs() releaseRunAs()} method.</li>
 523  
      * </ul>
 524  
      *
 525  
      * @param principals the identity to 'run as', aka the identity to <em>assume</em> indefinitely.
 526  
      * @throws NullPointerException  if the specified principals collection is {@code null} or empty.
 527  
      * @throws IllegalStateException if this {@code Subject} does not yet have an identity of its own.
 528  
      * @since 1.0
 529  
      */
 530  
     void runAs(PrincipalCollection principals) throws NullPointerException, IllegalStateException;
 531  
 
 532  
     /**
 533  
      * Returns {@code true} if this {@code Subject} is 'running as' another identity other than its original one or
 534  
      * {@code false} otherwise (normal {@code Subject} state).  See the {@link #runAs runAs} method for more
 535  
      * information.
 536  
      *
 537  
      * @return {@code true} if this {@code Subject} is 'running as' another identity other than its original one or
 538  
      *         {@code false} otherwise (normal {@code Subject} state).
 539  
      * @see #runAs
 540  
      * @since 1.0
 541  
      */
 542  
     boolean isRunAs();
 543  
 
 544  
     /**
 545  
      * Returns the previous 'pre run as' identity of this {@code Subject} before assuming the current
 546  
      * {@link #runAs runAs} identity, or {@code null} if this {@code Subject} is not operating under an assumed
 547  
      * identity (normal state). See the {@link #runAs runAs} method for more information.
 548  
      *
 549  
      * @return the previous 'pre run as' identity of this {@code Subject} before assuming the current
 550  
      *         {@link #runAs runAs} identity, or {@code null} if this {@code Subject} is not operating under an assumed
 551  
      *         identity (normal state).
 552  
      * @see #runAs
 553  
      * @since 1.0
 554  
      */
 555  
     PrincipalCollection getPreviousPrincipals();
 556  
 
 557  
     /**
 558  
      * Releases the current 'run as' (assumed) identity and reverts back to the previous 'pre run as'
 559  
      * identity that existed before {@code #runAs runAs} was called.
 560  
      * <p/>
 561  
      * This method returne 'run as' (assumed) identity being released or {@code null} if this {@code Subject} is not
 562  
      * operating under an assumed identity.
 563  
      *
 564  
      * @return the 'run as' (assumed) identity being released or {@code null} if this {@code Subject} is not operating
 565  
      *         under an assumed identity.
 566  
      * @see #runAs
 567  
      * @since 1.0
 568  
      */
 569  
     PrincipalCollection releaseRunAs();
 570  
 
 571  
     /**
 572  
      * Builder design pattern implementation for creating {@link Subject} instances in a simplified way without
 573  
      * requiring knowledge of Shiro's construction techniques.
 574  
      * <p/>
 575  
      * <b>NOTE</b>: This is provided for framework development support only and should typically never be used by
 576  
      * application developers.  {@code Subject} instances should generally be acquired by using
 577  
      * <code>SecurityUtils.{@link SecurityUtils#getSubject() getSubject()}</code>
 578  
      * <h4>Usage</h4>
 579  
      * The simplest usage of this builder is to construct an anonymous, session-less {@code Subject} instance:
 580  
      * <pre>
 581  
      * Subject subject = new Subject.{@link #Builder() Builder}().{@link #buildSubject() buildSubject()};</pre>
 582  
      * The default, no-arg {@code Subject.Builder()} constructor shown above will use the application's
 583  
      * currently accessible {@code SecurityManager} via
 584  
      * <code>SecurityUtils.{@link SecurityUtils#getSecurityManager() getSecurityManager()}</code>.  You may also
 585  
      * specify the exact {@code SecurityManager} instance to be used by the additional
 586  
      * <code>Subject.{@link #Builder(org.apache.shiro.mgt.SecurityManager) Builder(securityManager)}</code>
 587  
      * constructor if desired.
 588  
      * <p/>
 589  
      * All other methods may be called before the {@link #buildSubject() buildSubject()} method to
 590  
      * provide context on how to construct the {@code Subject} instance.  For example, if you have a session id and
 591  
      * want to acquire the {@code Subject} that 'owns' that session (assuming the session exists and is not expired):
 592  
      * <pre>
 593  
      * Subject subject = new Subject.Builder().sessionId(sessionId).buildSubject();</pre>
 594  
      * <p/>
 595  
      * Similarly, if you want a {@code Subject} instance reflecting a certain identity:
 596  
      * <pre>
 597  
      * PrincipalCollection principals = new SimplePrincipalCollection("username", <em>yourRealmName</em>);
 598  
      * Subject subject = new Subject.Builder().principals(principals).build();</pre>
 599  
      * <p/>
 600  
      * <b>Note*</b> that the returned {@code Subject} instance is <b>not</b> automatically bound to the application (thread)
 601  
      * for further use.  That is,
 602  
      * {@link org.apache.shiro.SecurityUtils SecurityUtils}.{@link org.apache.shiro.SecurityUtils#getSubject() getSubject()}
 603  
      * will not automatically return the same instance as what is returned by the builder.  It is up to the framework
 604  
      * developer to bind the built {@code Subject} for continued use if desired.
 605  
      *
 606  
      * @since 1.0
 607  
      */
 608  
     public static class Builder {
 609  
 
 610  
         /**
 611  
          * Hold all contextual data via the Builder instance's method invocations to be sent to the
 612  
          * {@code SecurityManager} during the {@link #buildSubject} call.
 613  
          */
 614  
         private final SubjectContext subjectContext;
 615  
 
 616  
         /**
 617  
          * The SecurityManager to invoke during the {@link #buildSubject} call.
 618  
          */
 619  
         private final SecurityManager securityManager;
 620  
 
 621  
         /**
 622  
          * Constructs a new {@link Subject.Builder} instance, using the {@code SecurityManager} instance available
 623  
          * to the calling code as determined by a call to {@link org.apache.shiro.SecurityUtils#getSecurityManager()}
 624  
          * to build the {@code Subject} instance.
 625  
          */
 626  
         public Builder() {
 627  12
             this(SecurityUtils.getSecurityManager());
 628  12
         }
 629  
 
 630  
         /**
 631  
          * Constructs a new {@link Subject.Builder} instance which will use the specified {@code SecurityManager} when
 632  
          * building the {@code Subject} instance.
 633  
          *
 634  
          * @param securityManager the {@code SecurityManager} to use when building the {@code Subject} instance.
 635  
          */
 636  29
         public Builder(SecurityManager securityManager) {
 637  29
             if (securityManager == null) {
 638  0
                 throw new NullPointerException("SecurityManager method argument cannot be null.");
 639  
             }
 640  29
             this.securityManager = securityManager;
 641  29
             this.subjectContext = newSubjectContextInstance();
 642  29
             if (this.subjectContext == null) {
 643  0
                 throw new IllegalStateException("Subject instance returned from 'newSubjectContextInstance' " +
 644  
                         "cannot be null.");
 645  
             }
 646  29
             this.subjectContext.setSecurityManager(securityManager);
 647  29
         }
 648  
 
 649  
         /**
 650  
          * Creates a new {@code SubjectContext} instance to be used to populate with subject contextual data that
 651  
          * will then be sent to the {@code SecurityManager} to create a new {@code Subject} instance.
 652  
          *
 653  
          * @return a new {@code SubjectContext} instance
 654  
          */
 655  
         protected SubjectContext newSubjectContextInstance() {
 656  29
             return new DefaultSubjectContext();
 657  
         }
 658  
 
 659  
         /**
 660  
          * Returns the backing context used to build the {@code Subject} instance, available to subclasses
 661  
          * since the {@code context} class attribute is marked as {@code private}.
 662  
          *
 663  
          * @return the backing context used to build the {@code Subject} instance, available to subclasses.
 664  
          */
 665  
         protected SubjectContext getSubjectContext() {
 666  0
             return this.subjectContext;
 667  
         }
 668  
 
 669  
         /**
 670  
          * Enables building a {@link Subject Subject} instance that owns the {@link Session Session} with the
 671  
          * specified {@code sessionId}.
 672  
          * <p/>
 673  
          * Usually when specifying a {@code sessionId}, no other {@code Builder} methods would be specified because
 674  
          * everything else (principals, inet address, etc) can usually be reconstructed based on the referenced
 675  
          * session alone.  In other words, this is almost always sufficient:
 676  
          * <pre>
 677  
          * new Subject.Builder().sessionId(sessionId).buildSubject();</pre>
 678  
          * <p/>
 679  
          * <b>Although simple in concept, this method provides very powerful functionality previously absent in almost
 680  
          * all Java environments:</b>
 681  
          * <p/>
 682  
          * The ability to reference a {@code Subject} and their server-side session
 683  
          * <em>across clients of different mediums</em> such as web applications, Java applets,
 684  
          * standalone C# clients over XML-RPC and/or SOAP, and many others. This is a <em>huge</em>
 685  
          * benefit in heterogeneous enterprise applications.
 686  
          * <p/>
 687  
          * To maintain session integrity across client mediums, the {@code sessionId} <b>must</b> be transmitted
 688  
          * to all client mediums securely (e.g. over SSL) to prevent man-in-the-middle attacks.  This
 689  
          * is nothing new - all web applications are susceptible to the same problem when transmitting
 690  
          * {@code Cookie}s or when using URL rewriting.  As long as the
 691  
          * {@code sessionId} is transmitted securely, session integrity can be maintained.
 692  
          *
 693  
          * @param sessionId the id of the session that backs the desired Subject being acquired.
 694  
          * @return this {@code Builder} instance for method chaining.
 695  
          */
 696  
         public Builder sessionId(Serializable sessionId) {
 697  0
             if (sessionId != null) {
 698  0
                 this.subjectContext.setSessionId(sessionId);
 699  
             }
 700  0
             return this;
 701  
         }
 702  
 
 703  
         /**
 704  
          * Ensures the {@code Subject} being built will reflect the specified host name or IP as its originating
 705  
          * location.
 706  
          *
 707  
          * @param host the host name or IP address to use as the {@code Subject}'s originating location.
 708  
          * @return this {@code Builder} instance for method chaining.
 709  
          */
 710  
         public Builder host(String host) {
 711  0
             if (StringUtils.hasText(host)) {
 712  0
                 this.subjectContext.setHost(host);
 713  
             }
 714  0
             return this;
 715  
         }
 716  
 
 717  
         /**
 718  
          * Ensures the {@code Subject} being built will use the specified {@link Session} instance.  Note that it is
 719  
          * more common to use the {@link #sessionId sessionId} builder method rather than having to construct a
 720  
          * {@code Session} instance for this method.
 721  
          *
 722  
          * @param session the session to use as the {@code Subject}'s {@link Session}
 723  
          * @return this {@code Builder} instance for method chaining.
 724  
          */
 725  
         public Builder session(Session session) {
 726  0
             if (session != null) {
 727  0
                 this.subjectContext.setSession(session);
 728  
             }
 729  0
             return this;
 730  
         }
 731  
 
 732  
         /**
 733  
          * Ensures the {@code Subject} being built will reflect the specified principals (aka identity).
 734  
          * <p/>
 735  
          * For example, if your application's unique identifier for users is a {@code String} username, and you wanted
 736  
          * to create a {@code Subject} instance that reflected a user whose username is
 737  
          * '{@code jsmith}', and you knew the Realm that could acquire {@code jsmith}'s principals based on the username
 738  
          * was named &quot;{@code myRealm}&quot;, you might create the '{@code jsmith} {@code Subject} instance this
 739  
          * way:
 740  
          * <pre>
 741  
          * PrincipalCollection identity = new {@link org.apache.shiro.subject.SimplePrincipalCollection#SimplePrincipalCollection(Object, String) SimplePrincipalCollection}(&quot;jsmith&quot;, &quot;myRealm&quot;);
 742  
          * Subject jsmith = new Subject.Builder().principals(identity).buildSubject();</pre>
 743  
          * <p/>
 744  
          * Similarly, if your application's unique identifier for users is a {@code long} value (such as might be used
 745  
          * as a primary key in a relational database) and you were using a {@code JDBC}
 746  
          * {@code Realm} named, (unimaginatively) &quot;jdbcRealm&quot;, you might create the Subject
 747  
          * instance this way:
 748  
          * <pre>
 749  
          * long userId = //get user ID from somewhere
 750  
          * PrincipalCollection userIdentity = new {@link org.apache.shiro.subject.SimplePrincipalCollection#SimplePrincipalCollection(Object, String) SimplePrincipalCollection}(<em>userId</em>, &quot;jdbcRealm&quot;);
 751  
          * Subject user = new Subject.Builder().principals(identity).buildSubject();</pre>
 752  
          *
 753  
          * @param principals the principals to use as the {@code Subject}'s identity.
 754  
          * @return this {@code Builder} instance for method chaining.
 755  
          */
 756  
         public Builder principals(PrincipalCollection principals) {
 757  0
             if (!CollectionUtils.isEmpty(principals)) {
 758  0
                 this.subjectContext.setPrincipals(principals);
 759  
             }
 760  0
             return this;
 761  
         }
 762  
 
 763  
         /**
 764  
          * Configures whether or not the created Subject instance can create a new {@code Session} if one does not
 765  
          * already exist.  If set to {@code false}, any application calls to
 766  
          * {@code subject.getSession()} or {@code subject.getSession(true))} will result in a SessionException.
 767  
          * <p/>
 768  
          * This setting is {@code true} by default, as most applications find value in sessions.
 769  
          *
 770  
          * @param enabled whether or not the created Subject instance can create a new {@code Session} if one does not
 771  
          *                already exist.
 772  
          * @return this {@code Builder} instance for method chaining.
 773  
          * @since 1.2
 774  
          */
 775  
         public Builder sessionCreationEnabled(boolean enabled) {
 776  0
             this.subjectContext.setSessionCreationEnabled(enabled);
 777  0
             return this;
 778  
         }
 779  
 
 780  
         /**
 781  
          * Ensures the {@code Subject} being built will be considered
 782  
          * {@link org.apache.shiro.subject.Subject#isAuthenticated() authenticated}.  Per the
 783  
          * {@link org.apache.shiro.subject.Subject#isAuthenticated() isAuthenticated()} JavaDoc, be careful
 784  
          * when specifying {@code true} - you should know what you are doing and have a good reason for ignoring Shiro's
 785  
          * default authentication state mechanisms.
 786  
          *
 787  
          * @param authenticated whether or not the built {@code Subject} will be considered authenticated.
 788  
          * @return this {@code Builder} instance for method chaining.
 789  
          * @see org.apache.shiro.subject.Subject#isAuthenticated()
 790  
          */
 791  
         public Builder authenticated(boolean authenticated) {
 792  0
             this.subjectContext.setAuthenticated(authenticated);
 793  0
             return this;
 794  
         }
 795  
 
 796  
         /**
 797  
          * Allows custom attributes to be added to the underlying context {@code Map} used to construct the
 798  
          * {@link Subject} instance.
 799  
          * <p/>
 800  
          * A {@code null} key throws an {@link IllegalArgumentException}. A {@code null} value effectively removes
 801  
          * any previously stored attribute under the given key from the context map.
 802  
          * <p/>
 803  
          * <b>*NOTE*:</b> This method is only useful when configuring Shiro with a custom {@link SubjectFactory}
 804  
          * implementation.  This method allows end-users to append additional data to the context map which the
 805  
          * {@code SubjectFactory} implementation can use when building custom Subject instances. As such, this method
 806  
          * is only useful when a custom {@code SubjectFactory} implementation has been configured.
 807  
          *
 808  
          * @param attributeKey   the key under which the corresponding value will be stored in the context {@code Map}.
 809  
          * @param attributeValue the value to store in the context map under the specified {@code attributeKey}.
 810  
          * @return this {@code Builder} instance for method chaining.
 811  
          * @throws IllegalArgumentException if the {@code attributeKey} is {@code null}.
 812  
          * @see SubjectFactory#createSubject(SubjectContext)
 813  
          */
 814  
         public Builder contextAttribute(String attributeKey, Object attributeValue) {
 815  0
             if (attributeKey == null) {
 816  0
                 String msg = "Subject context map key cannot be null.";
 817  0
                 throw new IllegalArgumentException(msg);
 818  
             }
 819  0
             if (attributeValue == null) {
 820  0
                 this.subjectContext.remove(attributeKey);
 821  
             } else {
 822  0
                 this.subjectContext.put(attributeKey, attributeValue);
 823  
             }
 824  0
             return this;
 825  
         }
 826  
 
 827  
         /**
 828  
          * Creates and returns a new {@code Subject} instance reflecting the cumulative state acquired by the
 829  
          * other methods in this class.
 830  
          * <p/>
 831  
          * This {@code Builder} instance will still retain the underlying state after this method is called - it
 832  
          * will not clear it; repeated calls to this method will return multiple {@link Subject} instances, all
 833  
          * reflecting the exact same state.  If a new (different) {@code Subject} is to be constructed, a new
 834  
          * {@code Builder} instance must be created.
 835  
          * <p/>
 836  
          * <b>Note</b> that the returned {@code Subject} instance is <b>not</b> automatically bound to the application
 837  
          * (thread) for further use.  That is,
 838  
          * {@link org.apache.shiro.SecurityUtils SecurityUtils}.{@link org.apache.shiro.SecurityUtils#getSubject() getSubject()}
 839  
          * will not automatically return the same instance as what is returned by the builder.  It is up to the
 840  
          * framework developer to bind the returned {@code Subject} for continued use if desired.
 841  
          *
 842  
          * @return a new {@code Subject} instance reflecting the cumulative state acquired by the
 843  
          *         other methods in this class.
 844  
          */
 845  
         public Subject buildSubject() {
 846  29
             return this.securityManager.createSubject(this.subjectContext);
 847  
         }
 848  
     }
 849  
 
 850  
 }