001 /**
002 *
003 * Licensed to the Apache Software Foundation (ASF) under one or more
004 * contributor license agreements. See the NOTICE file distributed with
005 * this work for additional information regarding copyright ownership.
006 * The ASF licenses this file to You under the Apache License, Version 2.0
007 * (the "License"); you may not use this file except in compliance with
008 * the License. You may obtain a copy of the License at
009 *
010 * http://www.apache.org/licenses/LICENSE-2.0
011 *
012 * Unless required by applicable law or agreed to in writing, software
013 * distributed under the License is distributed on an "AS IS" BASIS,
014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
015 * See the License for the specific language governing permissions and
016 * limitations under the License.
017 */
018 package org.apache.geronimo.openejb;
019
020 import java.lang.reflect.Method;
021 import java.security.AccessControlContext;
022 import java.security.AccessControlException;
023 import java.security.Permission;
024 import java.security.Principal;
025 import java.util.Properties;
026
027 import javax.security.auth.Subject;
028 import javax.security.auth.login.LoginContext;
029 import javax.security.auth.login.LoginException;
030 import javax.security.jacc.EJBMethodPermission;
031
032 import org.apache.geronimo.security.ContextManager;
033 import org.apache.geronimo.security.SubjectId;
034 import org.apache.openejb.InterfaceType;
035 import org.apache.openejb.core.CoreDeploymentInfo;
036 import org.apache.openejb.core.ThreadContext;
037 import org.apache.openejb.core.security.jaas.UsernamePasswordCallbackHandler;
038 import org.apache.openejb.spi.SecurityService;
039
040 /**
041 * @version $Rev: 706640 $ $Date: 2008-10-21 14:44:05 +0000 (Tue, 21 Oct 2008) $
042 */
043 public class GeronimoSecurityService implements SecurityService {
044 public void init(Properties props) throws Exception {
045 }
046
047 public Object login(String user, String pass) throws LoginException {
048 return login("OpenEJB", user, pass);
049 }
050
051 public Object login(String securityRealm, String user, String pass) throws LoginException {
052 LoginContext context = ContextManager.login(securityRealm, new UsernamePasswordCallbackHandler(user, pass));
053
054 Subject subject = context.getSubject();
055 return ContextManager.getSubjectId(subject);
056 }
057
058 public void logout(Object securityIdentity) {
059 Subject subject = ContextManager.getRegisteredSubject((SubjectId) securityIdentity);
060 ContextManager.unregisterSubject(subject);
061 }
062
063 public void associate(Object securityIdentity) throws LoginException {
064 if (securityIdentity == null) {
065 return;
066 }
067
068 Subject subject = ContextManager.getRegisteredSubject((SubjectId) securityIdentity);
069 if (subject == null) {
070 return;
071 }
072 ContextManager.setCallers(subject, subject);
073 }
074
075 public Object disassociate() {
076 // this is only called before the thread is put back in the pool so it should be ok
077 ContextManager.popCallers(null);
078 return null;
079 }
080
081 public boolean isCallerAuthorized(Method method, InterfaceType typee) {
082 ThreadContext threadContext = ThreadContext.getThreadContext();
083
084 try {
085 CoreDeploymentInfo deploymentInfo = threadContext.getDeploymentInfo();
086
087 // if security is not enabled we are autorized
088 EjbDeployment ejbDeployment = deploymentInfo.get(EjbDeployment.class);
089 if (ejbDeployment == null || !ejbDeployment.isSecurityEnabled()) {
090 return true;
091 }
092
093 String ejbName = deploymentInfo.getEjbName();
094
095 InterfaceType type = deploymentInfo.getInterfaceType(method.getDeclaringClass());
096
097 String name = (type == null) ? null : type.getSpecName();
098
099 Permission permission = new EJBMethodPermission(ejbName, name, method);
100
101 AccessControlContext accessContext = ContextManager.getCurrentContext();
102
103 if (permission != null) accessContext.checkPermission(permission);
104
105 } catch (AccessControlException e) {
106 return false;
107 }
108 return true;
109 }
110
111 public boolean isCallerInRole(String role) {
112 if (role == null) throw new IllegalArgumentException("Role must not be null");
113
114 ThreadContext threadContext = ThreadContext.getThreadContext();
115
116 CoreDeploymentInfo deploymentInfo = threadContext.getDeploymentInfo();
117
118 // if security is not enabled we are not in that role
119 EjbDeployment ejbDeployment = deploymentInfo.get(EjbDeployment.class);
120 if (ejbDeployment == null || !ejbDeployment.isSecurityEnabled()) {
121 return false;
122 }
123
124 return ContextManager.isCallerInRole(deploymentInfo.getEjbName(), role);
125 }
126
127 public Principal getCallerPrincipal() {
128 // if security is not enabled, we don't have a principal
129 ThreadContext threadContext = ThreadContext.getThreadContext();
130 CoreDeploymentInfo deploymentInfo = threadContext.getDeploymentInfo();
131 EjbDeployment ejbDeployment = deploymentInfo.get(EjbDeployment.class);
132 if (ejbDeployment == null || !ejbDeployment.isSecurityEnabled()) {
133 return null;
134 }
135
136 Subject callerSubject = ContextManager.getCurrentCaller();
137 return ContextManager.getCurrentPrincipal(callerSubject);
138 }
139
140 //
141 // Unused
142 //
143
144 public Object getSecurityIdentity() {
145 return null;
146 }
147
148 public void setSecurityIdentity(Object securityIdentity) {
149 throw new UnsupportedOperationException();
150 }
151
152 public <T> T translateTo(Object securityIdentity, Class<T> type) {
153 throw new UnsupportedOperationException();
154 }
155
156 public Subject getCurrentSubject() {
157 throw new UnsupportedOperationException();
158 }
159
160 }