From: Mathieu Baudier Date: Mon, 9 Apr 2018 07:09:23 +0000 (+0200) Subject: Start dealing properly with remote node X-Git-Tag: argeo-commons-2.1.73~12 X-Git-Url: https://git.argeo.org/?a=commitdiff_plain;h=12c44296992a48de65fe6864a6ed005f03264fcf;p=lgpl%2Fargeo-commons.git Start dealing properly with remote node --- diff --git a/org.argeo.cms/src/org/argeo/cms/internal/jcr/RepositoryBuilder.java b/org.argeo.cms/src/org/argeo/cms/internal/jcr/RepositoryBuilder.java index 622600d3c..d5f3a20cd 100644 --- a/org.argeo.cms/src/org/argeo/cms/internal/jcr/RepositoryBuilder.java +++ b/org.argeo.cms/src/org/argeo/cms/internal/jcr/RepositoryBuilder.java @@ -101,7 +101,14 @@ public class RepositoryBuilder { } } else { try { - homePath = Paths.get(new URI(homeUri)).toAbsolutePath(); + URI uri = new URI(homeUri); + String host = uri.getHost(); + if (host == null || host.trim().equals("")) { + homePath = Paths.get(uri).toAbsolutePath(); + } else { + // TODO remote at this stage? + throw new IllegalArgumentException("Cannot manage repository path for host " + host); + } } catch (URISyntaxException e) { throw new CmsException("Invalid repository home URI", e); } diff --git a/org.argeo.cms/src/org/argeo/cms/internal/jcr/repository-memory.xml b/org.argeo.cms/src/org/argeo/cms/internal/jcr/repository-memory.xml index 738ed5bbd..3630a149d 100644 --- a/org.argeo.cms/src/org/argeo/cms/internal/jcr/repository-memory.xml +++ b/org.argeo.cms/src/org/argeo/cms/internal/jcr/repository-memory.xml @@ -23,6 +23,10 @@ + + + diff --git a/org.argeo.cms/src/org/argeo/cms/internal/kernel/CmsDeployment.java b/org.argeo.cms/src/org/argeo/cms/internal/kernel/CmsDeployment.java index 917b15a9a..7134517f3 100644 --- a/org.argeo.cms/src/org/argeo/cms/internal/kernel/CmsDeployment.java +++ b/org.argeo.cms/src/org/argeo/cms/internal/kernel/CmsDeployment.java @@ -21,6 +21,7 @@ import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.apache.jackrabbit.commons.cnd.CndImporter; import org.apache.jackrabbit.core.RepositoryContext; +import org.apache.jackrabbit.core.RepositoryImpl; import org.argeo.cms.CmsException; import org.argeo.jcr.JcrUtils; import org.argeo.node.DataModelNamespace; @@ -211,11 +212,11 @@ public class CmsDeployment implements NodeDeployment { prepareDataModel(NodeConstants.NODE, KernelUtils.openAdminSession(deployedNodeRepository)); } - private void prepareHomeRepository(Repository deployedRepository) { + private void prepareHomeRepository(RepositoryImpl deployedRepository) { Hashtable regProps = new Hashtable(); regProps.put(NodeConstants.CN, NodeConstants.HOME); // regProps.put(LEGACY_JCR_REPOSITORY_ALIAS, NodeConstants.HOME); - homeRepository = new HomeRepository(deployedRepository); + homeRepository = new HomeRepository(deployedRepository, false); // register bc.registerService(Repository.class, homeRepository, regProps); diff --git a/org.argeo.cms/src/org/argeo/cms/internal/kernel/CmsFsProvider.java b/org.argeo.cms/src/org/argeo/cms/internal/kernel/CmsFsProvider.java index f42646ec5..614ff6c49 100644 --- a/org.argeo.cms/src/org/argeo/cms/internal/kernel/CmsFsProvider.java +++ b/org.argeo.cms/src/org/argeo/cms/internal/kernel/CmsFsProvider.java @@ -10,11 +10,13 @@ import java.util.Map; import javax.jcr.Node; import javax.jcr.Repository; +import javax.jcr.RepositoryFactory; import javax.jcr.Session; import org.argeo.cms.CmsException; import org.argeo.cms.auth.CurrentUser; import org.argeo.jackrabbit.fs.AbstractJackrabbitFsProvider; +import org.argeo.jcr.JcrUtils; import org.argeo.jcr.fs.JcrFileSystem; import org.argeo.jcr.fs.JcrFsException; import org.argeo.node.NodeConstants; @@ -42,12 +44,23 @@ public class CmsFsProvider extends AbstractJackrabbitFsProvider { throw new FileSystemAlreadyExistsException("CMS file system already exists for user " + username); try { - Repository repository = bc.getService( - bc.getServiceReferences(Repository.class, "(cn=" + NodeConstants.HOME + ")").iterator().next()); - Session session = repository.login(); - JcrFileSystem fileSystem = new JcrFileSystem(this, session); - fileSystems.put(username, fileSystem); - return fileSystem; + String host = uri.getHost(); + if (host != null && !host.trim().equals("")) { + URI repoUri = new URI("http", uri.getUserInfo(), uri.getHost(), uri.getPort(), "/jcr/node", null, null); + RepositoryFactory repositoryFactory = bc.getService(bc.getServiceReference(RepositoryFactory.class)); + Repository repository = NodeUtils.getRepositoryByUri(repositoryFactory, repoUri.toString()); + Session session = repository.login("main"); + JcrFileSystem fileSystem = new JcrFileSystem(this, session); + fileSystems.put(username, fileSystem); + return fileSystem; + } else { + Repository repository = bc.getService( + bc.getServiceReferences(Repository.class, "(cn=" + NodeConstants.HOME + ")").iterator().next()); + Session session = repository.login(); + JcrFileSystem fileSystem = new JcrFileSystem(this, session); + fileSystems.put(username, fileSystem); + return fileSystem; + } } catch (Exception e) { throw new CmsException("Cannot open file system " + uri + " for user " + username, e); } diff --git a/org.argeo.cms/src/org/argeo/cms/internal/kernel/HomeRepository.java b/org.argeo.cms/src/org/argeo/cms/internal/kernel/HomeRepository.java index 9ab66ffb8..b4f65bef7 100644 --- a/org.argeo.cms/src/org/argeo/cms/internal/kernel/HomeRepository.java +++ b/org.argeo.cms/src/org/argeo/cms/internal/kernel/HomeRepository.java @@ -39,36 +39,41 @@ class HomeRepository extends JcrRepositoryWrapper implements KernelConstants { private SimpleDateFormat usersDatePath = new SimpleDateFormat("YYYY/MM"); - public HomeRepository(Repository repository) { + private final boolean remote; + + public HomeRepository(Repository repository, boolean remote) { super(repository); + this.remote = remote; putDescriptor(NodeConstants.CN, NodeConstants.HOME); - LoginContext lc; - try { - lc = new LoginContext(NodeConstants.LOGIN_CONTEXT_DATA_ADMIN); - lc.login(); - } catch (javax.security.auth.login.LoginException e1) { - throw new CmsException("Cannot login as systrem", e1); - } - Subject.doAs(lc.getSubject(), new PrivilegedAction() { - - @Override - public Void run() { - try { - Session adminSession = getRepository().login(); - initJcr(adminSession); - } catch (RepositoryException e) { - throw new CmsException("Cannot init JCR home", e); - } - return null; + if (!remote) { + LoginContext lc; + try { + lc = new LoginContext(NodeConstants.LOGIN_CONTEXT_DATA_ADMIN); + lc.login(); + } catch (javax.security.auth.login.LoginException e1) { + throw new CmsException("Cannot login as systrem", e1); } + Subject.doAs(lc.getSubject(), new PrivilegedAction() { + + @Override + public Void run() { + try { + Session adminSession = getRepository().login(); + initJcr(adminSession); + } catch (RepositoryException e) { + throw new CmsException("Cannot init JCR home", e); + } + return null; + } - }); + }); + } } @Override protected void processNewSession(Session session) { String username = session.getUserID(); - if (username == null) + if (username == null || username.toString().equals("")) return; if (session.getUserID().equals(NodeConstants.ROLE_ANONYMOUS)) return; @@ -98,7 +103,7 @@ class HomeRepository extends JcrRepositoryWrapper implements KernelConstants { JcrUtils.addPrivilege(adminSession, groupsBasePath, NodeConstants.ROLE_USER_ADMIN, Privilege.JCR_READ); adminSession.save(); } catch (RepositoryException e) { - throw new CmsException("Cannot initialize node user admin", e); + throw new CmsException("Cannot initialize home repository", e); } finally { JcrUtils.logoutQuietly(adminSession); } diff --git a/org.argeo.cms/src/org/argeo/cms/internal/kernel/KernelConstants.java b/org.argeo.cms/src/org/argeo/cms/internal/kernel/KernelConstants.java index f8bce9cf6..f221d0cdb 100644 --- a/org.argeo.cms/src/org/argeo/cms/internal/kernel/KernelConstants.java +++ b/org.argeo.cms/src/org/argeo/cms/internal/kernel/KernelConstants.java @@ -41,4 +41,5 @@ public interface KernelConstants { // avoid dependencies String CONTEXT_NAME_PROP = "contextName"; String JACKRABBIT_REPOSITORY_URI = "org.apache.jackrabbit.repository.uri"; + String JACKRABBIT_REMOTE_DEFAULT_WORKSPACE = "org.apache.jackrabbit.spi2davex.WorkspaceNameDefault"; } diff --git a/org.argeo.cms/src/org/argeo/cms/internal/kernel/NodeLogger.java b/org.argeo.cms/src/org/argeo/cms/internal/kernel/NodeLogger.java index 116cf98ab..f7d6df811 100644 --- a/org.argeo.cms/src/org/argeo/cms/internal/kernel/NodeLogger.java +++ b/org.argeo.cms/src/org/argeo/cms/internal/kernel/NodeLogger.java @@ -52,6 +52,7 @@ import org.argeo.node.ArgeoLogListener; import org.argeo.node.ArgeoLogger; import org.argeo.node.NodeConstants; import org.argeo.osgi.useradmin.UserAdminConf; +import org.osgi.framework.Bundle; import org.osgi.framework.Constants; import org.osgi.framework.ServiceReference; import org.osgi.service.cm.ConfigurationAdmin; @@ -191,6 +192,10 @@ class NodeLogger implements ArgeoLogger, LogListener { private String msg(LogEntry status) { StringBuilder sb = new StringBuilder(); sb.append(status.getMessage()); + Bundle bundle = status.getBundle(); + if (bundle != null) { + sb.append(" '" + bundle.getSymbolicName() + "'"); + } ServiceReference sr = status.getServiceReference(); if (sr != null) { sb.append(' '); diff --git a/org.argeo.cms/src/org/argeo/cms/internal/kernel/NodeRepositoryFactory.java b/org.argeo.cms/src/org/argeo/cms/internal/kernel/NodeRepositoryFactory.java index 2e3e78f0d..f83eb9476 100644 --- a/org.argeo.cms/src/org/argeo/cms/internal/kernel/NodeRepositoryFactory.java +++ b/org.argeo.cms/src/org/argeo/cms/internal/kernel/NodeRepositoryFactory.java @@ -28,6 +28,7 @@ import javax.jcr.RepositoryFactory; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.apache.jackrabbit.jcr2dav.Jcr2davRepositoryFactory; +import org.argeo.cms.internal.jcr.RepoConf; import org.argeo.jcr.ArgeoJcrException; import org.argeo.node.NodeConstants; import org.osgi.framework.BundleContext; @@ -84,15 +85,16 @@ class NodeRepositoryFactory implements RepositoryFactory { // check if remote Repository repository; String uri = null; - if (parameters.containsKey(NodeConstants.LABELED_URI)) + if (parameters.containsKey(RepoConf.labeledUri.name())) uri = parameters.get(NodeConstants.LABELED_URI).toString(); else if (parameters.containsKey(KernelConstants.JACKRABBIT_REPOSITORY_URI)) uri = parameters.get(KernelConstants.JACKRABBIT_REPOSITORY_URI).toString(); if (uri != null) { - if (uri.startsWith("http"))// http, https - repository = createRemoteRepository(uri); - else if (uri.startsWith("file"))// http, https + if (uri.startsWith("http")) {// http, https + Object defaultWorkspace = parameters.get(RepoConf.defaultWorkspace.name()); + repository = createRemoteRepository(uri, defaultWorkspace != null ? defaultWorkspace.toString() : null); + } else if (uri.startsWith("file"))// http, https repository = createFileRepository(uri, parameters); else if (uri.startsWith("vm")) { // log.warn("URI " + uri + " should have been managed by generic @@ -120,9 +122,11 @@ class NodeRepositoryFactory implements RepositoryFactory { return repository; } - protected Repository createRemoteRepository(String uri) throws RepositoryException { + protected Repository createRemoteRepository(String uri, String defaultWorkspace) throws RepositoryException { Map params = new HashMap(); params.put(KernelConstants.JACKRABBIT_REPOSITORY_URI, uri); + if (defaultWorkspace != null) + params.put(KernelConstants.JACKRABBIT_REMOTE_DEFAULT_WORKSPACE, defaultWorkspace); Repository repository = new Jcr2davRepositoryFactory().getRepository(params); if (repository == null) throw new ArgeoJcrException("Remote Davex repository " + uri + " not found"); @@ -190,8 +194,7 @@ class NodeRepositoryFactory implements RepositoryFactory { } /** - * Called after the repository has been initialised. Does nothing by - * default. + * Called after the repository has been initialised. Does nothing by default. */ @SuppressWarnings("rawtypes") protected void postInitialization(Repository repository, Map parameters) { @@ -199,7 +202,7 @@ class NodeRepositoryFactory implements RepositoryFactory { } public void setFileRepositoryConfiguration(Resource fileRepositoryConfiguration) { -// this.fileRepositoryConfiguration = fileRepositoryConfiguration; + // this.fileRepositoryConfiguration = fileRepositoryConfiguration; } } diff --git a/org.argeo.cms/src/org/argeo/cms/internal/kernel/RepositoryServiceFactory.java b/org.argeo.cms/src/org/argeo/cms/internal/kernel/RepositoryServiceFactory.java index b718043d9..97a3e8d5a 100644 --- a/org.argeo.cms/src/org/argeo/cms/internal/kernel/RepositoryServiceFactory.java +++ b/org.argeo.cms/src/org/argeo/cms/internal/kernel/RepositoryServiceFactory.java @@ -1,13 +1,18 @@ package org.argeo.cms.internal.kernel; +import java.net.URI; import java.util.Dictionary; import java.util.HashMap; import java.util.Map; +import javax.jcr.Repository; +import javax.jcr.RepositoryFactory; + import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.apache.jackrabbit.core.RepositoryContext; import org.argeo.cms.CmsException; +import org.argeo.cms.internal.jcr.RepoConf; import org.argeo.cms.internal.jcr.RepositoryBuilder; import org.argeo.node.NodeConstants; import org.argeo.util.LangUtils; @@ -43,19 +48,59 @@ class RepositoryServiceFactory implements ManagedServiceFactory { } try { - RepositoryBuilder repositoryBuilder = new RepositoryBuilder(); - RepositoryContext repositoryContext = repositoryBuilder.createRepositoryContext(properties); - repositories.put(pid, repositoryContext); - Dictionary props = LangUtils.dico(Constants.SERVICE_PID, pid); - // props.put(ArgeoJcrConstants.JCR_REPOSITORY_URI, - // properties.get(RepoConf.labeledUri.name())); - Object cn = properties.get(NodeConstants.CN); - if (cn != null) { - props.put(NodeConstants.CN, cn); -// props.put(NodeConstants.JCR_REPOSITORY_ALIAS, cn); - pidToCn.put(pid, cn); + Object labeledUri = properties.get(RepoConf.labeledUri.name()); + if (labeledUri == null) { + RepositoryBuilder repositoryBuilder = new RepositoryBuilder(); + RepositoryContext repositoryContext = repositoryBuilder.createRepositoryContext(properties); + repositories.put(pid, repositoryContext); + Dictionary props = LangUtils.dico(Constants.SERVICE_PID, pid); + // props.put(ArgeoJcrConstants.JCR_REPOSITORY_URI, + // properties.get(RepoConf.labeledUri.name())); + Object cn = properties.get(NodeConstants.CN); + if (cn != null) { + props.put(NodeConstants.CN, cn); + // props.put(NodeConstants.JCR_REPOSITORY_ALIAS, cn); + pidToCn.put(pid, cn); + } + bc.registerService(RepositoryContext.class, repositoryContext, props); + } else { + try { + Object cn = properties.get(NodeConstants.CN); + Object defaultWorkspace = properties.get(RepoConf.defaultWorkspace.name()); + if (defaultWorkspace == null) + defaultWorkspace = RepoConf.defaultWorkspace.getDefault(); + URI uri = new URI(labeledUri.toString()); + RepositoryFactory repositoryFactory = bc + .getService(bc.getServiceReference(RepositoryFactory.class)); + Map parameters = new HashMap(); + parameters.put(RepoConf.labeledUri.name(), uri.toString()); + parameters.put(RepoConf.defaultWorkspace.name(), defaultWorkspace.toString()); + Repository repository = repositoryFactory.getRepository(parameters); + // Repository repository = NodeUtils.getRepositoryByUri(repositoryFactory, + // uri.toString()); + Dictionary props = LangUtils.dico(Constants.SERVICE_PID, pid); + props.put(RepoConf.labeledUri.name(), + new URI(uri.getScheme(), null, uri.getHost(), uri.getPort(), uri.getPath(), null, null) + .toString()); + if (cn != null) { + props.put(NodeConstants.CN, cn); + // props.put(NodeConstants.JCR_REPOSITORY_ALIAS, cn); + pidToCn.put(pid, cn); + } + bc.registerService(Repository.class, repository, props); + + // home + // TODO make a sperate home configurable + if (cn.equals(NodeConstants.NODE)) { + Dictionary homeProps = LangUtils.dico(NodeConstants.CN, NodeConstants.HOME); + HomeRepository homeRepository = new HomeRepository(repository, true); + bc.registerService(Repository.class, homeRepository, homeProps); + } + } catch (Exception e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } } - bc.registerService(RepositoryContext.class, repositoryContext, props); } catch (Exception e) { throw new CmsException("Cannot create Jackrabbit repository " + pid, e); }