2 * Copyright (C) 2007-2012 Mathieu Baudier
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
16 package org
.argeo
.security
.jcr
;
18 import java
.util
.ArrayList
;
19 import java
.util
.HashMap
;
20 import java
.util
.List
;
23 import javax
.jcr
.Credentials
;
24 import javax
.jcr
.Node
;
25 import javax
.jcr
.Repository
;
26 import javax
.jcr
.RepositoryException
;
27 import javax
.jcr
.RepositoryFactory
;
28 import javax
.jcr
.Session
;
29 import javax
.jcr
.SimpleCredentials
;
30 import javax
.jcr
.Value
;
32 import org
.argeo
.ArgeoException
;
33 import org
.argeo
.jcr
.ArgeoJcrConstants
;
34 import org
.argeo
.jcr
.ArgeoNames
;
35 import org
.argeo
.jcr
.JcrUtils
;
36 import org
.argeo
.security
.NodeAuthenticationToken
;
37 import org
.springframework
.security
.Authentication
;
38 import org
.springframework
.security
.AuthenticationException
;
39 import org
.springframework
.security
.BadCredentialsException
;
40 import org
.springframework
.security
.GrantedAuthority
;
41 import org
.springframework
.security
.GrantedAuthorityImpl
;
42 import org
.springframework
.security
.providers
.AuthenticationProvider
;
44 /** Connects to a JCR repository and delegates authentication to it. */
45 public class RemoteJcrAuthenticationProvider
implements AuthenticationProvider
,
47 private RepositoryFactory repositoryFactory
;
49 public Authentication
authenticate(Authentication authentication
)
50 throws AuthenticationException
{
51 NodeAuthenticationToken siteAuth
= (NodeAuthenticationToken
) authentication
;
52 String url
= siteAuth
.getUrl();
59 SimpleCredentials sp
= new SimpleCredentials(siteAuth
.getName(),
60 siteAuth
.getCredentials().toString().toCharArray());
62 Repository repository
= getRepository(url
, sp
);
63 if (repository
== null)
66 String workspace
= siteAuth
.getSecurityWorkspace();
67 session
= repository
.login(sp
, workspace
);
68 Node userHome
= JcrUtils
.getUserHome(session
);
69 if (userHome
== null || !userHome
.hasNode(ArgeoNames
.ARGEO_PROFILE
))
70 throw new ArgeoException("No profile for user "
71 + siteAuth
.getName() + " in security workspace "
72 + siteAuth
.getSecurityWorkspace() + " of "
74 userProfile
= userHome
.getNode(ArgeoNames
.ARGEO_PROFILE
);
75 } catch (RepositoryException e
) {
76 throw new BadCredentialsException(
77 "Cannot authenticate " + siteAuth
, e
);
81 JcrUserDetails
.checkAccountStatus(userProfile
);
82 // retrieve remote roles
83 List
<GrantedAuthority
> authoritiesList
= new ArrayList
<GrantedAuthority
>();
84 if (userProfile
.hasProperty(ArgeoNames
.ARGEO_REMOTE_ROLES
)) {
85 Value
[] roles
= userProfile
.getProperty(
86 ArgeoNames
.ARGEO_REMOTE_ROLES
).getValues();
87 for (int i
= 0; i
< roles
.length
; i
++)
88 authoritiesList
.add(new GrantedAuthorityImpl(roles
[i
]
92 // create authenticated objects
93 GrantedAuthority
[] authorities
= authoritiesList
94 .toArray(new GrantedAuthority
[authoritiesList
.size()]);
95 JcrUserDetails userDetails
= new JcrUserDetails(userProfile
,
96 siteAuth
.getCredentials().toString(), authorities
);
97 NodeAuthenticationToken authenticated
= new NodeAuthenticationToken(
98 siteAuth
, authorities
);
99 authenticated
.setDetails(userDetails
);
100 return authenticated
;
101 } catch (RepositoryException e
) {
102 throw new ArgeoException(
103 "Unexpected exception when authenticating to " + url
, e
);
107 protected Repository
getRepository(String url
, Credentials credentials
)
108 throws RepositoryException
{
109 Map
<String
, String
> parameters
= new HashMap
<String
, String
>();
110 parameters
.put(ArgeoJcrConstants
.JCR_REPOSITORY_URI
, url
);
111 return repositoryFactory
.getRepository(parameters
);
114 @SuppressWarnings("rawtypes")
115 public boolean supports(Class authentication
) {
116 return NodeAuthenticationToken
.class.isAssignableFrom(authentication
);
119 public void setRepositoryFactory(RepositoryFactory repositoryFactory
) {
120 this.repositoryFactory
= repositoryFactory
;