001: package ru.emdev.EmForge.svn;
002:
003: import org.acegisecurity.Authentication;
004: import org.acegisecurity.context.SecurityContextHolder;
005: import org.apache.commons.lang.StringUtils;
006: import org.apache.commons.logging.Log;
007: import org.apache.commons.logging.LogFactory;
008: import org.springframework.beans.factory.FactoryBean;
009: import org.springframework.beans.factory.InitializingBean;
010: import org.tmatesoft.svn.core.SVNException;
011: import org.tmatesoft.svn.core.SVNURL;
012: import org.tmatesoft.svn.core.auth.ISVNAuthenticationManager;
013: import org.tmatesoft.svn.core.internal.io.dav.DAVRepositoryFactory;
014: import org.tmatesoft.svn.core.internal.io.fs.FSRepositoryFactory;
015: import org.tmatesoft.svn.core.internal.io.svn.SVNRepositoryFactoryImpl;
016: import org.tmatesoft.svn.core.io.SVNRepository;
017: import org.tmatesoft.svn.core.io.SVNRepositoryFactory;
018: import org.tmatesoft.svn.core.wc.SVNWCUtil;
019:
020: import ru.emdev.EmForge.security.EmForgeAnonymousProcessingFilter;
021: import ru.emdev.EmForge.security.EmForgeUserDetails;
022:
023: /**
024: * Bean-Factory for creation SVN Repository It creates repostiory, connected to the repositoryPath and authenticated
025: * with using current user crediteals It also stored name of user, used for repository creation - and if it was
026: * changed-made reconnection. This is not application-wide bean - but user specific(session or request scope - depends
027: * from how it is defined) First -lets try to make it request-scoped, because SvnKit is not thread safe
028: */
029: public class UserSvnRepositoryFactory implements FactoryBean,
030: InitializingBean, SvnRepositoryFactory {
031:
032: protected final Log logger = LogFactory.getLog(getClass());
033:
034: /** Path to the repository */
035: private String m_repositoryPath;
036:
037: private SVNRepository m_repository;
038: private EmForgeAnonymousProcessingFilter m_anonymousProvider;
039:
040: /**
041: * @param i_repositoryPath
042: */
043: public void setRepositoryPath(String i_repositoryPath) {
044:
045: m_repositoryPath = i_repositoryPath;
046: }
047:
048: /**
049: * @param i_anonymousProvider
050: */
051: public void setAnonymousProvider(
052: EmForgeAnonymousProcessingFilter i_anonymousProvider) {
053:
054: m_anonymousProvider = i_anonymousProvider;
055: }
056:
057: /**
058: * @see ru.emdev.EmForge.svn.SvnRepositoryFactory#isHasRepository()
059: */
060: public Boolean isHasRepository() {
061:
062: return !StringUtils.isEmpty(m_repositoryPath);
063: }
064:
065: /**
066: * @see org.springframework.beans.factory.FactoryBean#getObject()
067: */
068: public Object getObject() throws Exception {
069:
070: return getSvnRepository();
071: }
072:
073: /**
074: * @see org.springframework.beans.factory.FactoryBean#getObjectType()
075: */
076: public Class<?> getObjectType() {
077:
078: return SVNRepository.class;
079: }
080:
081: /**
082: * @see org.springframework.beans.factory.FactoryBean#isSingleton()
083: */
084: public boolean isSingleton() {
085:
086: return true;
087: }
088:
089: /**
090: * @see org.springframework.beans.factory.InitializingBean#afterPropertiesSet()
091: */
092: public void afterPropertiesSet() throws Exception {
093:
094: // initialize subversion
095: DAVRepositoryFactory.setup();
096: SVNRepositoryFactoryImpl.setup();
097: FSRepositoryFactory.setup();
098:
099: if (StringUtils.isEmpty(m_repositoryPath)) {
100: throw new IllegalArgumentException(
101: "Repository path should be specified!");
102: }
103: }
104:
105: /**
106: * Creates repository (if it is required)
107: *
108: * @return
109: * @throws Exception
110: * @see ru.emdev.EmForge.svn.SvnRepositoryFactory#getSvnRepository()
111: */
112: public SVNRepository getSvnRepository() throws SVNException {
113:
114: Authentication auth = null;
115: EmForgeUserDetails emForgeUser = null;
116: try {
117: auth = SecurityContextHolder.getContext()
118: .getAuthentication();
119: } catch (Exception ex) {
120: // it may happens ( for example for Lucene-Search thread) we have no authentication
121: // In this case we should create new anonymous user by ourself
122: logger
123: .error("Cannot find authentication information - use anonymous!!!");
124: auth = m_anonymousProvider.createAuthentication(null);
125: }
126:
127: if (auth == null) {
128: logger
129: .error("Cannot find authentication information - use anonymous!!!");
130: auth = m_anonymousProvider.createAuthentication(null);
131: }
132:
133: assert auth != null;
134: emForgeUser = (EmForgeUserDetails) auth.getPrincipal();
135: assert emForgeUser != null;
136:
137: if (m_repository == null) {
138: // create it
139: assert m_repositoryPath != null;
140:
141: SVNURL url = SVNURL.parseURIEncoded(m_repositoryPath);
142: m_repository = SVNRepositoryFactory.create(url);
143:
144: String vcUserName = emForgeUser.getVcUserName();
145: String vcPassword = emForgeUser.getVcPassword();
146:
147: if (vcPassword == null) {
148: vcPassword = auth.getCredentials().toString();
149: }
150:
151: logger.debug("Logging into SVN " + m_repositoryPath
152: + " as " + emForgeUser.getDisplayName());
153: ISVNAuthenticationManager authManager = SVNWCUtil
154: .createDefaultAuthenticationManager(vcUserName,
155: vcPassword);
156: m_repository.setAuthenticationManager(authManager);
157:
158: }
159:
160: return m_repository;
161: }
162: }
|