2015-03-09 1 views
0

Я использую плагин Spring Security Ldap.Grails Spring Security: как я могу использовать свой собственный домен для моего LdapAuthenticator?

У меня есть свой домен пользователя с только именем пользователя и только с именем пользователя. Я хотел бы аутентифицировать его с именем пользователя и паролем из LDAP и проверить, существует ли имя пользователя в базе данных.

домена: имя пользователя, что я использовал для входа в систему

class User { 
    String username 
    String userId 

    static mapping = { 
     id name: 'userId' 
     version: false 
     id generator: 'assigned' 
    } 

    static constrainsts = { 
     userId blank: false, nullable: false, size:1..12 
     username blank: false, unique: true, size:1..12 
    } 
} 

Пользовательские UserDetailsContextMapper:

class CustomUserDetailsContextMapper implements UserDetailsContextMapper { 

    def springSecurityService 

    private static final List NO_ROLES = [new SimpleGrantedAuthority(SpringSecurityUtils.NO_ROLE)] 

    @Override 
    @Transactional 
    UserDetails mapUserFromContext(DirContextOperations ctx, String username, Collection<SimpleGrantedAuthority> authority) { 
     SecUser user = SecUser.findByUsername(username) 

     if (!user) throw new UsernameNotFoundException('User not found', username) 

     return new CustomUserDetails(
      user.userid, username 
      ) 
    } 

    @Override 
    public void mapUserToContext(UserDetails user, DirContextAdapter ctx) { 
     throw new IllegalStateException("Only retrieving data from LDAP is currently supported") 
    } 
} 

Пользовательские UserDetails:

class CustomUserDetails extends GrailsUser { 
    private final Object _id; 

    public CustomUserDetails(
     String userId, String username) { 

     super(username, password, enabled, accountNonExpired, 
      credentialsNonExpired, accountNonLocked, authorities, userId); 
    } 

    public Object getDomainClass() { 
     return null; 
    } 

} 

Я был в состоянии проверить подлинность моего пользователя, который доступен в Active Directory, но не в базе данных. Он возвращает «Пользователь не найден». Но при проверке подлинности пользователя, который доступен в Active Directory и в базе данных, я получаю сообщение об ошибке, где «конструктор не соответствует»

Здесь ошибка я столкнулся ...

[/sampleproject].[default] Servlet.service() for servlet [default] in context with path [/sampleproject] threw exception 
groovy.lang.GroovyRuntimeException: Could not find matching constructor for: com.security.CustomUserDetails(java.lang.String, null, java.lang.Boolean, java.lang.Boolean, java.lang.Boolean, java.lang.Boolean, null, java.lang.String) 
    at groovy.lang.MetaClassImpl.invokeConstructor(MetaClassImpl.java:1723) 
    at groovy.lang.MetaClassImpl.invokeConstructor(MetaClassImpl.java:1526) 
    at groovy.lang.ExpandoMetaClass.invokeConstructor(ExpandoMetaClass.java:675) 
    at org.codehaus.groovy.runtime.callsite.MetaClassConstructorSite.callConstructor(MetaClassConstructorSite.java:46) 
    at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCallConstructor(CallSiteArray.java:57) 
    at org.codehaus.groovy.runtime.callsite.AbstractCallSite.callConstructor(AbstractCallSite.java:182) 
    at com.security.CustomUserDetailsContextMapper.mapUserFromContext(CustomUserDetailsContextMapper.groovy:41) 
    at com.security.CustomUserDetailsContextMapper$$FastClassBySpringCGLIB$$f40634de.invoke(<generated>) 
    at org.springframework.cglib.proxy.MethodProxy.invoke(MethodProxy.java:204) 
    at org.springframework.aop.framework.CglibAopProxy$CglibMethodInvocation.invokeJoinpoint(CglibAopProxy.java:708) 
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:157) 
    at org.springframework.transaction.interceptor.TransactionInterceptor$1.proceedWithInvocation(TransactionInterceptor.java:98) 
    at org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:262) 
    at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:95) 
    at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:179) 
    at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:644) 
    at com.security.CustomUserDetailsContextMapper$$EnhancerBySpringCGLIB$$e13e0669.mapUserFromContext(<generated>) 
    at org.springframework.security.ldap.authentication.AbstractLdapAuthenticationProvider.authenticate(AbstractLdapAuthenticationProvider.java:63) 
    at org.springframework.security.authentication.ProviderManager.authenticate(ProviderManager.java:156) 
    at org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter.attemptAuthentication(UsernamePasswordAuthenticationFilter.java:94) 
    at grails.plugin.springsecurity.web.authentication.RequestHolderAuthenticationFilter.attemptAuthentication(RequestHolderAuthenticationFilter.java:76) 
    at org.springframework.security.web.authentication.AbstractAuthenticationProcessingFilter.doFilter(AbstractAuthenticationProcessingFilter.java:211) 
    at grails.plugin.springsecurity.web.authentication.RequestHolderAuthenticationFilter.doFilter(RequestHolderAuthenticationFilter.java:49) 
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342) 
    at grails.plugin.springsecurity.web.authentication.logout.MutableLogoutFilter.doFilter(MutableLogoutFilter.java:82) 
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342) 
    at org.springframework.security.web.context.SecurityContextPersistenceFilter.doFilter(SecurityContextPersistenceFilter.java:87) 
    at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342) 
    at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:192) 
    at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:160) 
    at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:344) 
    at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:261) 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241) 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208) 
    at org.codehaus.groovy.grails.web.servlet.mvc.GrailsWebRequestFilter.doFilterInternal(GrailsWebRequestFilter.java:69) 
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241) 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208) 
    at org.codehaus.groovy.grails.web.filters.HiddenHttpMethodFilter.doFilterInternal(HiddenHttpMethodFilter.java:67) 
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241) 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208) 
    at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:88) 
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) 
    at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:344) 
    at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:261) 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241) 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208) 
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:220) 
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:122) 
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:171) 
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:103) 
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:116) 
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:408) 
    at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1070) 
    at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:611) 
    at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:316) 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142) 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617) 
    at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61) 
    at java.lang.Thread.run(Thread.java:745) 
+0

Если есть исключения, добавьте (m | соответствующие детали) к вопросу. – cfrick

ответ

0

Я полагаю, вы внесли некоторые изменения, чтобы удалить проприетарную информацию и/или упростить код, но, как и в настоящее время, класс CustomUserDetails очень сломан.

Имя класса CustomUserDetails, и у вас есть то, что кажется конструктором, за исключением его названия UAMSUserDetails. GrailsUser имеет id свойство, а его конструктор подписи

public GrailsUser(String username, String password, boolean enabled, 
        boolean accountNonExpired, boolean credentialsNonExpired, 
        boolean accountNonLocked, 
        Collection<GrantedAuthority> authorities, Object id) 

так что ваш призыв к super недопустим - количество аргументов неправильно (вы не передавая userId как id) и ни один из password, enabled, accountNonExpired, credentialsNonExpired, accountNonLocked, или authorities определяется. Предполагая, что вы хотите значения по умолчанию, разве это не должно быть что-то вроде этого?

class UAMSUserDetails extends GrailsUser { 

    UAMSUserDetails(String userId, String username) { 
     super(username, null/*password*/, true, true, true, true, 
      null/*authorities*/, userId) 
    } 

    def getDomainClass() { null } 
} 
+0

Спасибо за ответ! Это мой первый раз публиковать здесь и делать редактирование (и я получил много изменений из-за нажатия «enter» в поле «summary summary»). Да, я хочу эти значения в своих CustomUserDetails. Я пробовал применить этот код, и он показывает ошибку, которую я добавил в свой вопрос. – Dzoinks