You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@chemistry.apache.org by fg...@apache.org on 2010/04/15 12:33:51 UTC
svn commit: r934361 [2/9] - in /incubator/chemistry/opencmis/trunk:
chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/
chemistry-opencmis-client/chemistry-opencmis-client-bindings/s...
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/RepositoryServiceImpl.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/RepositoryServiceImpl.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/RepositoryServiceImpl.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/RepositoryServiceImpl.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,185 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.chemistry.opencmis.client.bindings.impl;
+
+import java.io.Serializable;
+import java.math.BigInteger;
+import java.util.List;
+
+import org.apache.chemistry.opencmis.client.bindings.spi.CmisSpi;
+import org.apache.chemistry.opencmis.client.bindings.spi.Session;
+import org.apache.chemistry.opencmis.commons.api.ExtensionsData;
+import org.apache.chemistry.opencmis.commons.api.TypeDefinition;
+import org.apache.chemistry.opencmis.commons.api.TypeDefinitionContainer;
+import org.apache.chemistry.opencmis.commons.api.TypeDefinitionList;
+import org.apache.chemistry.opencmis.commons.provider.RepositoryInfoData;
+import org.apache.chemistry.opencmis.commons.provider.RepositoryService;
+
+/**
+ * Repository Service implementation.
+ *
+ * Passes requests to the SPI and handles caching.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public class RepositoryServiceImpl implements RepositoryService, Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private final Session fSession;
+
+ /**
+ * Constructor.
+ */
+ public RepositoryServiceImpl(Session session) {
+ fSession = session;
+ }
+
+ public RepositoryInfoData getRepositoryInfo(String repositoryId, ExtensionsData extension) {
+ RepositoryInfoData result = null;
+ boolean hasExtension = (extension != null) && (!extension.getExtensions().isEmpty());
+
+ RepositoryInfoCache cache = CmisBindingsHelper.getRepositoryInfoCache(fSession);
+
+ // if extension is not set, check the cache first
+ if (!hasExtension) {
+ result = cache.get(repositoryId);
+ if (result != null) {
+ return result;
+ }
+ }
+
+ // it was not in the cache -> get the SPI and fetch the repository info
+ CmisSpi spi = CmisBindingsHelper.getSPI(fSession);
+ result = spi.getRepositoryService().getRepositoryInfo(repositoryId, extension);
+
+ // put it into the cache
+ if (!hasExtension) {
+ cache.put(result);
+ }
+
+ return result;
+ }
+
+ public List<RepositoryInfoData> getRepositoryInfos(ExtensionsData extension) {
+ List<RepositoryInfoData> result = null;
+ boolean hasExtension = (extension != null) && (!extension.getExtensions().isEmpty());
+
+ // get the SPI and fetch the repository infos
+ CmisSpi spi = CmisBindingsHelper.getSPI(fSession);
+ result = spi.getRepositoryService().getRepositoryInfos(extension);
+
+ // put it into the cache
+ if (!hasExtension && (result != null)) {
+ RepositoryInfoCache cache = CmisBindingsHelper.getRepositoryInfoCache(fSession);
+ for (RepositoryInfoData rid : result) {
+ cache.put(rid);
+ }
+ }
+
+ return result;
+ }
+
+ public TypeDefinitionList getTypeChildren(String repositoryId, String typeId,
+ Boolean includePropertyDefinitions, BigInteger maxItems, BigInteger skipCount,
+ ExtensionsData extension) {
+ TypeDefinitionList result = null;
+ boolean hasExtension = (extension != null) && (!extension.getExtensions().isEmpty());
+ boolean propDefs = (includePropertyDefinitions == null ? false : includePropertyDefinitions
+ .booleanValue());
+
+ // get the SPI and fetch the type definitions
+ CmisSpi spi = CmisBindingsHelper.getSPI(fSession);
+ result = spi.getRepositoryService().getTypeChildren(repositoryId, typeId,
+ includePropertyDefinitions, maxItems, skipCount, extension);
+
+ // put it into the cache
+ if (!hasExtension && propDefs && (result != null)) {
+ TypeDefinitionCache cache = CmisBindingsHelper.getTypeDefinitionCache(fSession);
+
+ for (TypeDefinition tdd : result.getList()) {
+ cache.put(repositoryId, tdd);
+ }
+ }
+
+ return result;
+ }
+
+ public TypeDefinition getTypeDefinition(String repositoryId, String typeId,
+ ExtensionsData extension) {
+ TypeDefinition result = null;
+ boolean hasExtension = (extension != null) && (!extension.getExtensions().isEmpty());
+
+ TypeDefinitionCache cache = CmisBindingsHelper.getTypeDefinitionCache(fSession);
+
+ // if extension is not set, check the cache first
+ if (!hasExtension) {
+ result = cache.get(repositoryId, typeId);
+ if (result != null) {
+ return result;
+ }
+ }
+
+ // it was not in the cache -> get the SPI and fetch the type definition
+ CmisSpi spi = CmisBindingsHelper.getSPI(fSession);
+ result = spi.getRepositoryService().getTypeDefinition(repositoryId, typeId, extension);
+
+ // put it into the cache
+ if (!hasExtension && (result != null)) {
+ cache.put(repositoryId, result);
+ }
+
+ return result;
+ }
+
+ public List<TypeDefinitionContainer> getTypeDescendants(String repositoryId, String typeId,
+ BigInteger depth, Boolean includePropertyDefinitions, ExtensionsData extension) {
+ List<TypeDefinitionContainer> result = null;
+ boolean hasExtension = (extension != null) && (!extension.getExtensions().isEmpty());
+ boolean propDefs = (includePropertyDefinitions == null ? false : includePropertyDefinitions
+ .booleanValue());
+
+ // get the SPI and fetch the type definitions
+ CmisSpi spi = CmisBindingsHelper.getSPI(fSession);
+ result = spi.getRepositoryService().getTypeDescendants(repositoryId, typeId, depth,
+ includePropertyDefinitions, extension);
+
+ // put it into the cache
+ if (!hasExtension && propDefs && (result != null)) {
+ TypeDefinitionCache cache = CmisBindingsHelper.getTypeDefinitionCache(fSession);
+ addToTypeCache(cache, repositoryId, result);
+ }
+
+ return result;
+ }
+
+ private void addToTypeCache(TypeDefinitionCache cache, String repositoryId,
+ List<TypeDefinitionContainer> containers) {
+ if (containers == null) {
+ return;
+ }
+
+ for (TypeDefinitionContainer container : containers) {
+ cache.put(repositoryId, container.getTypeDefinition());
+ addToTypeCache(cache, repositoryId, container.getChildren());
+ }
+ }
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/RepositoryServiceImpl.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/RepositoryServiceImpl.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/RepositoryServiceImpl.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/SessionImpl.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/SessionImpl.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/SessionImpl.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/SessionImpl.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,145 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.impl;
+
+import java.io.Serializable;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
+
+import org.apache.chemistry.opencmis.client.bindings.spi.Session;
+
+/**
+ * CMIS binding session implementation.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public class SessionImpl implements Session {
+
+ private static final long serialVersionUID = 1L;
+
+ private Map<String, Object> fData;
+
+ private final ReentrantReadWriteLock fLock = new ReentrantReadWriteLock();
+
+ /**
+ * Constructor.
+ */
+ public SessionImpl() {
+ fData = new HashMap<String, Object>();
+ }
+
+ public Object get(String key) {
+ Object value = null;
+
+ fLock.readLock().lock();
+ try {
+ value = fData.get(key);
+ }
+ finally {
+ fLock.readLock().unlock();
+ }
+
+ if (value instanceof TransientWrapper) {
+ return ((TransientWrapper) value).getObject();
+ }
+
+ return value;
+ }
+
+ public Object get(String key, Object defValue) {
+ Object value = get(key);
+ return (value == null ? defValue : value);
+ }
+
+ public int get(String key, int defValue) {
+ Object value = get(key);
+ int intValue = defValue;
+
+ if (value instanceof Integer) {
+ intValue = ((Integer) value).intValue();
+ }
+ else if (value instanceof String) {
+ try {
+ intValue = Integer.valueOf((String) value);
+ }
+ catch (NumberFormatException e) {
+ }
+ }
+
+ return intValue;
+ }
+
+ public void put(String key, Serializable obj) {
+ fLock.writeLock().lock();
+ try {
+ fData.put(key, obj);
+ }
+ finally {
+ fLock.writeLock().unlock();
+ }
+ }
+
+ public void put(String key, Object obj, boolean isTransient) {
+ Object value = (isTransient ? new TransientWrapper(obj) : obj);
+ if (!(value instanceof Serializable)) {
+ throw new IllegalArgumentException("Object must be serializable!");
+ }
+
+ fLock.writeLock().lock();
+ try {
+ fData.put(key, value);
+ }
+ finally {
+ fLock.writeLock().unlock();
+ }
+ }
+
+ public void remove(String key) {
+ fLock.writeLock().lock();
+ try {
+ fData.remove(key);
+ }
+ finally {
+ fLock.writeLock().unlock();
+ }
+ }
+
+ public void readLock() {
+ fLock.readLock().lock();
+ }
+
+ public void readUnlock() {
+ fLock.readLock().unlock();
+ }
+
+ public void writeLock() {
+ fLock.writeLock().lock();
+ }
+
+ public void writeUnlock() {
+ fLock.writeLock().unlock();
+ }
+
+ @Override
+ public String toString() {
+ return fData.toString();
+ }
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/SessionImpl.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/SessionImpl.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/SessionImpl.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TransientWrapper.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TransientWrapper.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TransientWrapper.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TransientWrapper.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,46 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.impl;
+
+import java.io.Serializable;
+
+/**
+ * Wrapper for transient objects in a cache.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public class TransientWrapper implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+ private transient Object fObject = null;
+
+ public TransientWrapper(Object object) {
+ fObject = object;
+ }
+
+ public Object getObject() {
+ return fObject;
+ }
+
+ @Override
+ public String toString() {
+ return (fObject == null ? "(no object)" : "(transient) " + fObject.toString());
+ }
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TransientWrapper.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TransientWrapper.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TransientWrapper.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TypeDefinitionCache.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TypeDefinitionCache.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TypeDefinitionCache.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TypeDefinitionCache.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,125 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.impl;
+
+import java.io.Serializable;
+
+import org.apache.chemistry.opencmis.client.bindings.cache.Cache;
+import org.apache.chemistry.opencmis.client.bindings.cache.impl.CacheImpl;
+import org.apache.chemistry.opencmis.client.bindings.cache.impl.LruCacheLevelImpl;
+import org.apache.chemistry.opencmis.client.bindings.cache.impl.MapCacheLevelImpl;
+import org.apache.chemistry.opencmis.client.bindings.spi.Session;
+import org.apache.chemistry.opencmis.commons.SessionParameter;
+import org.apache.chemistry.opencmis.commons.api.TypeDefinition;
+
+/**
+ * A cache for type definition objects.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public class TypeDefinitionCache implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private static final int CACHE_SIZE_REPOSITORIES = 10;
+ private static final int CACHE_SIZE_TYPES = 100;
+
+ private Cache fCache;
+
+ /**
+ * Constructor.
+ *
+ * @param session
+ * the session object
+ */
+ public TypeDefinitionCache(Session session) {
+ int repCount = session.get(SessionParameter.CACHE_SIZE_REPOSITORIES, CACHE_SIZE_REPOSITORIES);
+ if (repCount < 1) {
+ repCount = CACHE_SIZE_REPOSITORIES;
+ }
+
+ int typeCount = session.get(SessionParameter.CACHE_SIZE_TYPES, CACHE_SIZE_TYPES);
+ if (typeCount < 1) {
+ typeCount = CACHE_SIZE_TYPES;
+ }
+
+ fCache = new CacheImpl("Type Definition Cache");
+ fCache.initialize(new String[] {
+ MapCacheLevelImpl.class.getName() + " " + MapCacheLevelImpl.CAPACITY + "=" + repCount, // repository
+ LruCacheLevelImpl.class.getName() + " " + LruCacheLevelImpl.MAX_ENTRIES + "=" + typeCount // type
+ });
+ }
+
+ /**
+ * Adds a type definition object to the cache.
+ *
+ * @param repositoryId
+ * the repository id
+ * @param typeDefinition
+ * the type definition object
+ */
+ public void put(String repositoryId, TypeDefinition typeDefinition) {
+ if ((typeDefinition == null) || (typeDefinition.getId() == null)) {
+ return;
+ }
+
+ fCache.put(typeDefinition, repositoryId, typeDefinition.getId());
+ }
+
+ /**
+ * Retrieves a type definition object from the cache.
+ *
+ * @param repositoryId
+ * the repository id
+ * @param typeId
+ * the type id
+ * @return the type definition object or <code>null</code> if the object is not in the cache
+ */
+ public TypeDefinition get(String repositoryId, String typeId) {
+ return (TypeDefinition) fCache.get(repositoryId, typeId);
+ }
+
+ /**
+ * Removes a type definition object from the cache.
+ *
+ * @param repositoryId
+ * the repository id
+ * @param typeId
+ * the type id
+ */
+ public void remove(String repositoryId, String typeId) {
+ fCache.remove(repositoryId, typeId);
+ }
+
+ /**
+ * Removes all type definition objects of a repository from the cache.
+ *
+ * @param repositoryId
+ * the repository id
+ */
+ public void remove(String repositoryId) {
+ fCache.remove(repositoryId);
+ }
+
+ @Override
+ public String toString() {
+ return fCache.toString();
+ }
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TypeDefinitionCache.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TypeDefinitionCache.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/impl/TypeDefinitionCache.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/AbstractAuthenticationProvider.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/AbstractAuthenticationProvider.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/AbstractAuthenticationProvider.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/AbstractAuthenticationProvider.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,107 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.spi;
+
+import java.io.Serializable;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.chemistry.opencmis.commons.SessionParameter;
+import org.w3c.dom.Element;
+
+/**
+ * Authentication provider class.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public abstract class AbstractAuthenticationProvider implements Serializable {
+
+ private static final long serialVersionUID = 1L;
+
+ private Session fSession;
+
+ /**
+ * Sets the {@link Session} the authentication provider lives in.
+ */
+ public void setSession(Session session) {
+ fSession = session;
+ }
+
+ /**
+ * Returns {@link Session}.
+ */
+ public Session getSession() {
+ return fSession;
+ }
+
+ /**
+ * Returns a set of HTTP headers (key-value pairs) that should be added to a HTTP call. This will
+ * be called by the AtomPub and the Web Services binding. You might want to check the binding in
+ * use before you set the headers.
+ *
+ * @param url
+ * the URL of the HTTP call
+ *
+ * @return the HTTP headers or <code>null</code> if no additional headers should be set
+ */
+ public Map<String, List<String>> getHTTPHeaders(String url) {
+ return null;
+ }
+
+ /**
+ * Returns a SOAP header that should be added to a Web Services call.
+ *
+ * @param portObject
+ * the port object
+ *
+ * @return the SOAP headers or <code>null</code> if no additional headers should be set
+ */
+ public Element getSOAPHeaders(Object portObject) {
+ return null;
+ }
+
+ /**
+ * Gets the user name from the session.
+ *
+ * @return the user name or <code>null</code> if the user name is not set
+ */
+ protected String getUser() {
+ Object userObject = getSession().get(SessionParameter.USER);
+ if (userObject instanceof String) {
+ return (String) userObject;
+ }
+
+ return null;
+ }
+
+ /**
+ * Gets the password from the session.
+ *
+ * @return the password or <code>null</code> if the password is not set
+ */
+ protected String getPassword() {
+ Object passwordObject = getSession().get(SessionParameter.PASSWORD);
+ if (passwordObject instanceof String) {
+ return (String) passwordObject;
+ }
+
+ return null;
+ }
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/AbstractAuthenticationProvider.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/AbstractAuthenticationProvider.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/AbstractAuthenticationProvider.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpi.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpi.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpi.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpi.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,96 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.spi;
+
+import org.apache.chemistry.opencmis.commons.provider.AclService;
+import org.apache.chemistry.opencmis.commons.provider.DiscoveryService;
+import org.apache.chemistry.opencmis.commons.provider.MultiFilingService;
+import org.apache.chemistry.opencmis.commons.provider.NavigationService;
+import org.apache.chemistry.opencmis.commons.provider.ObjectService;
+import org.apache.chemistry.opencmis.commons.provider.PolicyService;
+import org.apache.chemistry.opencmis.commons.provider.RelationshipService;
+import org.apache.chemistry.opencmis.commons.provider.RepositoryService;
+import org.apache.chemistry.opencmis.commons.provider.VersioningService;
+
+/**
+ * CMIS SPI interface.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public interface CmisSpi {
+ /**
+ * Gets a Repository Service interface object.
+ */
+ RepositoryService getRepositoryService();
+
+ /**
+ * Gets a Navigation Service interface object.
+ */
+ NavigationService getNavigationService();
+
+ /**
+ * Gets an Object Service interface object.
+ */
+ ObjectService getObjectService();
+
+ /**
+ * Gets a Versioning Service interface object.
+ */
+ VersioningService getVersioningService();
+
+ /**
+ * Gets a Relationship Service interface object.
+ */
+ RelationshipService getRelationshipService();
+
+ /**
+ * Gets a Discovery Service interface object.
+ */
+ DiscoveryService getDiscoveryService();
+
+ /**
+ * Gets a Multifiling Service interface object.
+ */
+ MultiFilingService getMultiFilingService();
+
+ /**
+ * Gets an ACL Service interface object.
+ */
+ AclService getAclService();
+
+ /**
+ * Gets a Policy Service interface object.
+ */
+ PolicyService getPolicyService();
+
+ /**
+ * Clears all caches of the current session.
+ */
+ void clearAllCaches();
+
+ /**
+ * Clears all caches of the current session that are related to the given repository.
+ *
+ * @param repositoryId
+ * the repository id
+ */
+ void clearRepositoryCache(String repositoryId);
+
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpi.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpi.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpi.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpiFactory.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpiFactory.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpiFactory.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpiFactory.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,35 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.spi;
+
+/**
+ * CMIS SPI factory interface.
+ *
+ * <p>
+ * A class implementing this interface MUST provide a default constructor.
+ * </p>
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public interface CmisSpiFactory {
+
+ CmisSpi getSpiInstance(Session session);
+
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpiFactory.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpiFactory.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/CmisSpiFactory.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/Session.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/Session.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/Session.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/Session.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,80 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.spi;
+
+import java.io.Serializable;
+
+/**
+ * CMIS provider session interface.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public interface Session extends Serializable {
+
+ /**
+ * Gets a session value.
+ */
+ Object get(String key);
+
+ /**
+ * Returns a session value or the default value if the key doesn't exist.
+ */
+ Object get(String key, Object defValue);
+
+ /**
+ * Returns a session value or the default value if the key doesn't exist.
+ */
+ int get(String key, int defValue);
+
+ /**
+ * Adds a non-transient session value.
+ */
+ void put(String key, Serializable object);
+
+ /**
+ * Adds a session value.
+ */
+ void put(String key, Object object, boolean isTransient);
+
+ /**
+ * Removes a session value.
+ */
+ void remove(String key);
+
+ /**
+ * Acquires a read lock.
+ */
+ void readLock();
+
+ /**
+ * Releases a read lock.
+ */
+ void readUnlock();
+
+ /**
+ * Acquires a write lock.
+ */
+ void writeLock();
+
+ /**
+ * Releases a write lock.
+ */
+ void writeUnlock();
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/Session.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/Session.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/Session.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/StandardAuthenticationProvider.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/StandardAuthenticationProvider.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/StandardAuthenticationProvider.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/StandardAuthenticationProvider.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,179 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.spi;
+
+import java.io.UnsupportedEncodingException;
+import java.text.SimpleDateFormat;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.TimeZone;
+
+import javax.xml.parsers.DocumentBuilderFactory;
+import javax.xml.parsers.ParserConfigurationException;
+
+import org.apache.chemistry.opencmis.commons.SessionParameter;
+import org.apache.commons.codec.binary.Base64;
+import org.w3c.dom.Document;
+import org.w3c.dom.Element;
+
+/**
+ * Standard authentication provider class.
+ *
+ * Adds a basic authentication HTTP header and a WS-Security UsernameToken SOAP header.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public class StandardAuthenticationProvider extends AbstractAuthenticationProvider {
+
+ private static final long serialVersionUID = 1L;
+
+ private static final String WSSE_NAMESPACE = "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-1.0.xsd";
+ private static final String WSU_NAMESPACE = "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd";
+
+ @Override
+ public Map<String, List<String>> getHTTPHeaders(String url) {
+ Map<String, List<String>> result = null;
+
+ // only send HTTP header if configured
+ if (!isTrue(SessionParameter.AUTH_HTTP_BASIC)) {
+ return null;
+ }
+
+ // get user and password
+ String user = getUser();
+ String password = getPassword();
+
+ // if no user is set, don't create HTTP headers
+ if (user == null) {
+ return null;
+ }
+
+ if (password == null) {
+ password = "";
+ }
+
+ String authHeader = "";
+ try {
+ authHeader = "Basic "
+ + new String(Base64.encodeBase64((user + ":" + password).getBytes("ISO-8859-1")),
+ "ISO-8859-1");
+ }
+ catch (UnsupportedEncodingException e) {
+ // shouldn't happen...
+ return null;
+ }
+
+ result = new HashMap<String, List<String>>();
+ result.put("Authorization", Collections.singletonList(authHeader));
+
+ return result;
+ }
+
+ @Override
+ public Element getSOAPHeaders(Object portObject) {
+ // get user and password
+ String user = getUser();
+ String password = getPassword();
+
+ // only send SOAP header if configured
+ if (!isTrue(SessionParameter.AUTH_SOAP_USERNAMETOKEN)) {
+ return null;
+ }
+
+ // if no user is set, don't create SOAP header
+ if (user == null) {
+ return null;
+ }
+
+ if (password == null) {
+ password = "";
+ }
+
+ // set time
+ SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss'Z'");
+ sdf.setTimeZone(TimeZone.getTimeZone("UTC"));
+ long created = System.currentTimeMillis();
+ long expires = created + 24 * 60 * 60 * 1000; // 24 hours
+
+ // create the SOAP header
+ try {
+ Document document = DocumentBuilderFactory.newInstance().newDocumentBuilder().newDocument();
+
+ Element wsseSecurityElement = document.createElementNS(WSSE_NAMESPACE, "Security");
+
+ Element wsuTimestampElement = document.createElementNS(WSU_NAMESPACE, "Timestamp");
+ wsseSecurityElement.appendChild(wsuTimestampElement);
+
+ Element tsCreatedElement = document.createElementNS(WSU_NAMESPACE, "Created");
+ tsCreatedElement.setTextContent(sdf.format(created));
+ wsuTimestampElement.appendChild(tsCreatedElement);
+
+ Element tsExpiresElement = document.createElementNS(WSU_NAMESPACE, "Expires");
+ tsExpiresElement.setTextContent(sdf.format(expires));
+ wsuTimestampElement.appendChild(tsExpiresElement);
+
+ Element usernameTokenElement = document.createElementNS(WSSE_NAMESPACE, "UsernameToken");
+ wsseSecurityElement.appendChild(usernameTokenElement);
+
+ Element usernameElement = document.createElementNS(WSSE_NAMESPACE, "Username");
+ usernameElement.setTextContent(user);
+ usernameTokenElement.appendChild(usernameElement);
+
+ Element passwordElement = document.createElementNS(WSSE_NAMESPACE, "Password");
+ passwordElement.setTextContent(password);
+ passwordElement
+ .setAttribute("Type",
+ "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-username-token-profile-1.0#PasswordText");
+ usernameTokenElement.appendChild(passwordElement);
+
+ Element createdElement = document.createElementNS(WSU_NAMESPACE, "Created");
+ createdElement.setTextContent(sdf.format(created));
+ usernameTokenElement.appendChild(createdElement);
+
+ return wsseSecurityElement;
+ }
+ catch (ParserConfigurationException e) {
+ // shouldn't happen...
+ e.printStackTrace();
+ }
+
+ return null;
+ }
+
+ /**
+ * Returns <code>true</code> if the given parameter exists in the session and is set to true,
+ * <code>false</code> otherwise.
+ */
+ private boolean isTrue(String parameterName) {
+ Object value = getSession().get(parameterName);
+
+ if (value instanceof Boolean) {
+ return ((Boolean) value).booleanValue();
+ }
+
+ if (value instanceof String) {
+ return Boolean.parseBoolean((String) value);
+ }
+
+ return false;
+ }
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/StandardAuthenticationProvider.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/StandardAuthenticationProvider.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/StandardAuthenticationProvider.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AbstractAtomPubService.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AbstractAtomPubService.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AbstractAtomPubService.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AbstractAtomPubService.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,806 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.spi.atompub;
+
+import static org.apache.chemistry.opencmis.commons.impl.Converter.convert;
+
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.math.BigInteger;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.apache.chemistry.opencmis.client.bindings.spi.Session;
+import org.apache.chemistry.opencmis.client.bindings.spi.atompub.objects.Acl;
+import org.apache.chemistry.opencmis.client.bindings.spi.atompub.objects.AtomBase;
+import org.apache.chemistry.opencmis.client.bindings.spi.atompub.objects.AtomElement;
+import org.apache.chemistry.opencmis.client.bindings.spi.atompub.objects.AtomEntry;
+import org.apache.chemistry.opencmis.client.bindings.spi.atompub.objects.AtomLink;
+import org.apache.chemistry.opencmis.client.bindings.spi.atompub.objects.RepositoryWorkspace;
+import org.apache.chemistry.opencmis.client.bindings.spi.atompub.objects.ServiceDoc;
+import org.apache.chemistry.opencmis.commons.PropertyIds;
+import org.apache.chemistry.opencmis.commons.SessionParameter;
+import org.apache.chemistry.opencmis.commons.api.ExtensionsData;
+import org.apache.chemistry.opencmis.commons.api.TypeDefinition;
+import org.apache.chemistry.opencmis.commons.enums.AclPropagation;
+import org.apache.chemistry.opencmis.commons.enums.IncludeRelationships;
+import org.apache.chemistry.opencmis.commons.exceptions.CmisBaseException;
+import org.apache.chemistry.opencmis.commons.exceptions.CmisConnectionException;
+import org.apache.chemistry.opencmis.commons.exceptions.CmisConstraintException;
+import org.apache.chemistry.opencmis.commons.exceptions.CmisInvalidArgumentException;
+import org.apache.chemistry.opencmis.commons.exceptions.CmisNotSupportedException;
+import org.apache.chemistry.opencmis.commons.exceptions.CmisObjectNotFoundException;
+import org.apache.chemistry.opencmis.commons.exceptions.CmisPermissionDeniedException;
+import org.apache.chemistry.opencmis.commons.exceptions.CmisRuntimeException;
+import org.apache.chemistry.opencmis.commons.impl.Constants;
+import org.apache.chemistry.opencmis.commons.impl.JaxBHelper;
+import org.apache.chemistry.opencmis.commons.impl.ReturnVersion;
+import org.apache.chemistry.opencmis.commons.impl.UrlBuilder;
+import org.apache.chemistry.opencmis.commons.impl.dataobjects.AccessControlEntryImpl;
+import org.apache.chemistry.opencmis.commons.impl.dataobjects.AccessControlListImpl;
+import org.apache.chemistry.opencmis.commons.impl.dataobjects.AccessControlPrincipalDataImpl;
+import org.apache.chemistry.opencmis.commons.impl.jaxb.CmisAccessControlListType;
+import org.apache.chemistry.opencmis.commons.impl.jaxb.CmisObjectType;
+import org.apache.chemistry.opencmis.commons.impl.jaxb.CmisPropertiesType;
+import org.apache.chemistry.opencmis.commons.impl.jaxb.CmisPropertyId;
+import org.apache.chemistry.opencmis.commons.impl.jaxb.CmisRepositoryInfoType;
+import org.apache.chemistry.opencmis.commons.impl.jaxb.CmisTypeDefinitionType;
+import org.apache.chemistry.opencmis.commons.provider.AccessControlEntry;
+import org.apache.chemistry.opencmis.commons.provider.AccessControlList;
+import org.apache.chemistry.opencmis.commons.provider.ObjectData;
+import org.apache.chemistry.opencmis.commons.provider.RepositoryInfoData;
+
+/**
+ * Base class for all AtomPub clients.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public class AbstractAtomPubService {
+
+ protected enum IdentifierType {
+ ID, PATH
+ };
+
+ protected static final String NAME_COLLECTION = "collection";
+ protected static final String NAME_URI_TEMPLATE = "uritemplate";
+ protected static final String NAME_PATH_SEGMENT = "pathSegment";
+ protected static final String NAME_RELATIVE_PATH_SEGMENT = "relativePathSegment";
+ protected static final String NAME_NUM_ITEMS = "numItems";
+
+ private Session fSession;
+
+ /**
+ * Sets the current session.
+ */
+ protected void setSession(Session session) {
+ fSession = session;
+ }
+
+ /**
+ * Gets the current session.
+ */
+ protected Session getSession() {
+ return fSession;
+ }
+
+ /**
+ * Returns the service document URL of this session.
+ */
+ protected String getServiceDocURL() {
+ Object url = fSession.get(SessionParameter.ATOMPUB_URL);
+ if (url instanceof String) {
+ return (String) url;
+ }
+
+ return null;
+ }
+
+ // ---- link cache ----
+
+ /**
+ * Returns the link cache or creates a new cache if it doesn't exist.
+ */
+ protected LinkCache getLinkCache() {
+ LinkCache linkCache = (LinkCache) getSession().get(SpiSessionParameter.LINK_CACHE);
+ if (linkCache == null) {
+ linkCache = new LinkCache(getSession());
+ getSession().put(SpiSessionParameter.LINK_CACHE, linkCache);
+ }
+
+ return linkCache;
+ }
+
+ /**
+ * Gets a link from the cache.
+ */
+ protected String getLink(String repositoryId, String id, String rel, String type) {
+ if (repositoryId == null) {
+ throw new CmisInvalidArgumentException("Repository id must be set!");
+ }
+
+ if (id == null) {
+ throw new CmisInvalidArgumentException("Object id must be set!");
+ }
+
+ return getLinkCache().getLink(repositoryId, id, rel, type);
+ }
+
+ /**
+ * Gets a link from the cache.
+ */
+ protected String getLink(String repositoryId, String id, String rel) {
+ return getLink(repositoryId, id, rel, null);
+ }
+
+ /**
+ * Gets a link from the cache if it is there or loads it into the cache if it is not there.
+ */
+ protected String loadLink(String repositoryId, String id, String rel, String type) {
+ String link = getLink(repositoryId, id, rel, type);
+ if (link == null) {
+ getObjectInternal(repositoryId, IdentifierType.ID, id, ReturnVersion.THIS, null, null, null,
+ null, null, null, null);
+ link = getLink(repositoryId, id, rel, type);
+ }
+
+ return link;
+ }
+
+ /**
+ * Adds a link to the cache.
+ */
+ protected void addLink(String repositoryId, String id, String rel, String type, String link) {
+ getLinkCache().addLink(repositoryId, id, rel, type, link);
+ }
+
+ /**
+ * Adds a link to the cache.
+ */
+ protected void addLink(String repositoryId, String id, AtomLink link) {
+ getLinkCache().addLink(repositoryId, id, link.getRel(), link.getType(), link.getHref());
+ }
+
+ /**
+ * Removes all links of an object.
+ */
+ protected void removeLinks(String repositoryId, String id) {
+ getLinkCache().removeLinks(repositoryId, id);
+ }
+
+ /**
+ * Locks the link cache.
+ */
+ protected void lockLinks() {
+ getLinkCache().lockLinks();
+ }
+
+ /**
+ * Unlocks the link cache.
+ */
+ protected void unlockLinks() {
+ getLinkCache().unlockLinks();
+ }
+
+ /**
+ * Checks a link throw an appropriate exception.
+ */
+ protected void throwLinkException(String repositoryId, String id, String rel, String type) {
+ int index = getLinkCache().checkLink(repositoryId, id, rel, type);
+
+ switch (index) {
+ case 0:
+ throw new CmisObjectNotFoundException("Unknown repository!");
+ case 1:
+ throw new CmisObjectNotFoundException("Unknown object!");
+ case 2:
+ throw new CmisNotSupportedException(
+ "Operation not supported by the repository for this object!");
+ case 3:
+ throw new CmisNotSupportedException("No link with matching media type!");
+ case 4:
+ throw new CmisRuntimeException("Nothing wrong! Either this is a bug or threading issue.");
+ default:
+ throw new CmisRuntimeException("Unknown error!");
+ }
+ }
+
+ /**
+ * Gets a type link from the cache.
+ */
+ protected String getTypeLink(String repositoryId, String typeId, String rel, String type) {
+ if (repositoryId == null) {
+ throw new CmisInvalidArgumentException("Repository id must be set!");
+ }
+
+ if (typeId == null) {
+ throw new CmisInvalidArgumentException("Type id must be set!");
+ }
+
+ return getLinkCache().getTypeLink(repositoryId, typeId, rel, type);
+ }
+
+ /**
+ * Gets a type link from the cache.
+ */
+ protected String getTypeLink(String repositoryId, String typeId, String rel) {
+ return getTypeLink(repositoryId, typeId, rel, null);
+ }
+
+ /**
+ * Gets a link from the cache if it is there or loads it into the cache if it is not there.
+ */
+ protected String loadTypeLink(String repositoryId, String typeId, String rel, String type) {
+ String link = getTypeLink(repositoryId, typeId, rel, type);
+ if (link == null) {
+ getTypeDefinitionInternal(repositoryId, typeId);
+ link = getTypeLink(repositoryId, typeId, rel, type);
+ }
+
+ return link;
+ }
+
+ /**
+ * Adds a type link to the cache.
+ */
+ protected void addTypeLink(String repositoryId, String typeId, String rel, String type,
+ String link) {
+ getLinkCache().addTypeLink(repositoryId, typeId, rel, type, link);
+ }
+
+ /**
+ * Adds a type link to the cache.
+ */
+ protected void addTypeLink(String repositoryId, String typeId, AtomLink link) {
+ getLinkCache().addTypeLink(repositoryId, typeId, link.getRel(), link.getType(), link.getHref());
+ }
+
+ /**
+ * Removes all links of a type.
+ */
+ protected void removeTypeLinks(String repositoryId, String id) {
+ getLinkCache().removeTypeLinks(repositoryId, id);
+ }
+
+ /**
+ * Locks the type link cache.
+ */
+ protected void lockTypeLinks() {
+ getLinkCache().lockTypeLinks();
+ }
+
+ /**
+ * Unlocks the type link cache.
+ */
+ protected void unlockTypeLinks() {
+ getLinkCache().unlockTypeLinks();
+ }
+
+ /**
+ * Gets a collection from the cache.
+ */
+ protected String getCollection(String repositoryId, String collection) {
+ return getLinkCache().getCollection(repositoryId, collection);
+ }
+
+ /**
+ * Gets a collection from the cache if it is there or loads it into the cache if it is not there.
+ */
+ protected String loadCollection(String repositoryId, String collection) {
+ String link = getCollection(repositoryId, collection);
+ if (link == null) {
+ // cache repository info
+ getRepositoriesInternal(repositoryId);
+ link = getCollection(repositoryId, collection);
+ }
+
+ return link;
+ }
+
+ /**
+ * Adds a collection to the cache.
+ */
+ protected void addCollection(String repositoryId, String collection, String link) {
+ getLinkCache().addCollection(repositoryId, collection, link);
+ }
+
+ /**
+ * Gets a repository link from the cache.
+ */
+ protected String getRepositoryLink(String repositoryId, String rel) {
+ return getLinkCache().getRepositoryLink(repositoryId, rel);
+ }
+
+ /**
+ * Gets a repository link from the cache if it is there or loads it into the cache if it is not
+ * there.
+ */
+ protected String loadRepositoryLink(String repositoryId, String rel) {
+ String link = getRepositoryLink(repositoryId, rel);
+ if (link == null) {
+ // cache repository info
+ getRepositoriesInternal(repositoryId);
+ link = getRepositoryLink(repositoryId, rel);
+ }
+
+ return link;
+ }
+
+ /**
+ * Adds a repository link to the cache.
+ */
+ protected void addRepositoryLink(String repositoryId, String rel, String link) {
+ getLinkCache().addRepositoryLink(repositoryId, rel, link);
+ }
+
+ /**
+ * Adds a repository link to the cache.
+ */
+ protected void addRepositoryLink(String repositoryId, AtomLink link) {
+ addRepositoryLink(repositoryId, link.getRel(), link.getHref());
+ }
+
+ /**
+ * Gets an URI template from the cache.
+ */
+ protected String getTemplateLink(String repositoryId, String type, Map<String, Object> parameters) {
+ return getLinkCache().getTemplateLink(repositoryId, type, parameters);
+ }
+
+ /**
+ * Gets a template link from the cache if it is there or loads it into the cache if it is not
+ * there.
+ */
+ protected String loadTemplateLink(String repositoryId, String type, Map<String, Object> parameters) {
+ String link = getTemplateLink(repositoryId, type, parameters);
+ if (link == null) {
+ // cache repository info
+ getRepositoriesInternal(repositoryId);
+ link = getTemplateLink(repositoryId, type, parameters);
+ }
+
+ return link;
+ }
+
+ /**
+ * Adds an URI template to the cache.
+ */
+ protected void addTemplate(String repositoryId, String type, String link) {
+ getLinkCache().addTemplate(repositoryId, type, link);
+ }
+
+ // ---- exceptions ----
+
+ /**
+ * Converts a HTTP status code into an Exception.
+ */
+ protected CmisBaseException convertStatusCode(int code, String message, String errorContent,
+ Throwable t) {
+ switch (code) {
+ case 400:
+ return new CmisInvalidArgumentException(message, errorContent, t);
+ case 404:
+ return new CmisObjectNotFoundException(message, errorContent, t);
+ case 403:
+ return new CmisPermissionDeniedException(message, errorContent, t);
+ case 405:
+ return new CmisNotSupportedException(message, errorContent, t);
+ case 409:
+ return new CmisConstraintException(message, errorContent, t);
+ default:
+ return new CmisRuntimeException(message, errorContent, t);
+ }
+ }
+
+ // ---- helpers ----
+
+ protected boolean is(String name, AtomElement element) {
+ return name.equals(element.getName().getLocalPart());
+ }
+
+ protected boolean isStr(String name, AtomElement element) {
+ return is(name, element) && (element.getObject() instanceof String);
+ }
+
+ protected boolean isInt(String name, AtomElement element) {
+ return is(name, element) && (element.getObject() instanceof BigInteger);
+ }
+
+ protected boolean isNextLink(AtomElement element) {
+ return Constants.REL_NEXT.equals(((AtomLink) element.getObject()).getRel());
+ }
+
+ /**
+ * Creates a CMIS object that only contains an id in the property list.
+ */
+ protected CmisObjectType createIdObject(String objectId) {
+ CmisObjectType object = new CmisObjectType();
+
+ CmisPropertiesType properties = new CmisPropertiesType();
+ object.setProperties(properties);
+
+ CmisPropertyId idProperty = new CmisPropertyId();
+ properties.getProperty().add(idProperty);
+ idProperty.setPropertyDefinitionId(PropertyIds.CMIS_OBJECT_ID);
+ idProperty.getValue().add(objectId);
+
+ return object;
+ }
+
+ /**
+ * Parses an input stream.
+ */
+ @SuppressWarnings("unchecked")
+ protected <T extends AtomBase> T parse(InputStream stream, Class<T> clazz) {
+ AtomPubParser parser = new AtomPubParser(stream);
+
+ try {
+ parser.parse();
+ }
+ catch (Exception e) {
+ throw new CmisConnectionException("Parsing exception!", e);
+ }
+
+ AtomBase parseResult = parser.getResults();
+
+ if (!clazz.isInstance(parseResult)) {
+ throw new CmisConnectionException("Unexpected document! Received "
+ + (parseResult == null ? "something unknown" : parseResult.getType()) + "!");
+ }
+
+ return (T) parseResult;
+ }
+
+ /**
+ * Performs a GET on an URL, checks the response code and returns the result.
+ */
+ protected HttpUtils.Response read(UrlBuilder url) {
+ // make the call
+ HttpUtils.Response resp = HttpUtils.invokeGET(url, fSession);
+
+ // check response code
+ if (resp.getResponseCode() != 200) {
+ throw convertStatusCode(resp.getResponseCode(), resp.getResponseMessage(), resp
+ .getErrorContent(), null);
+ }
+
+ return resp;
+ }
+
+ /**
+ * Performs a POST on an URL, checks the response code and returns the result.
+ */
+ protected HttpUtils.Response post(UrlBuilder url, String contentType, HttpUtils.Output writer) {
+ // make the call
+ HttpUtils.Response resp = HttpUtils.invokePOST(url, contentType, writer, fSession);
+
+ // check response code
+ if (resp.getResponseCode() != 201) {
+ throw convertStatusCode(resp.getResponseCode(), resp.getResponseMessage(), resp
+ .getErrorContent(), null);
+ }
+
+ return resp;
+ }
+
+ /**
+ * Performs a PUT on an URL, checks the response code and returns the result.
+ */
+ protected HttpUtils.Response put(UrlBuilder url, String contentType, HttpUtils.Output writer) {
+ // make the call
+ HttpUtils.Response resp = HttpUtils.invokePUT(url, contentType, writer, fSession);
+
+ // check response code
+ if ((resp.getResponseCode() < 200) || (resp.getResponseCode() > 299)) {
+ throw convertStatusCode(resp.getResponseCode(), resp.getResponseMessage(), resp
+ .getErrorContent(), null);
+ }
+
+ return resp;
+ }
+
+ /**
+ * Performs a DELETE on an URL, checks the response code and returns the result.
+ */
+ protected void delete(UrlBuilder url) {
+ // make the call
+ HttpUtils.Response resp = HttpUtils.invokeDELETE(url, fSession);
+
+ // check response code
+ if (resp.getResponseCode() != 204) {
+ throw convertStatusCode(resp.getResponseCode(), resp.getResponseMessage(), resp
+ .getErrorContent(), null);
+ }
+ }
+
+ // ---- common operations ----
+
+ /**
+ * Checks if at least one ACE list is not empty.
+ */
+ protected boolean isAclMergeRequired(AccessControlList addAces, AccessControlList removeAces) {
+ return (addAces != null && addAces.getAces() != null && !addAces.getAces().isEmpty())
+ || (removeAces != null && removeAces.getAces() != null && !removeAces.getAces().isEmpty());
+ }
+
+ /**
+ * Merges the new ACL from original, add and remove ACEs lists.
+ */
+ protected AccessControlList mergeAcls(AccessControlList originalAces, AccessControlList addAces,
+ AccessControlList removeAces) {
+ Map<String, Set<String>> originals = convertAclToMap(originalAces);
+ Map<String, Set<String>> adds = convertAclToMap(addAces);
+ Map<String, Set<String>> removes = convertAclToMap(removeAces);
+ List<AccessControlEntry> newACEs = new ArrayList<AccessControlEntry>();
+
+ // iterate through the original ACEs
+ for (Map.Entry<String, Set<String>> ace : originals.entrySet()) {
+
+ // add permissions
+ Set<String> addPermissions = adds.get(ace.getKey());
+ if (addPermissions != null) {
+ ace.getValue().addAll(addPermissions);
+ }
+
+ // remove permissions
+ Set<String> removePermissions = removes.get(ace.getKey());
+ if (removePermissions != null) {
+ ace.getValue().removeAll(removePermissions);
+ }
+
+ // create new ACE
+ if (!ace.getValue().isEmpty()) {
+ newACEs.add(new AccessControlEntryImpl(new AccessControlPrincipalDataImpl(ace.getKey()),
+ new ArrayList<String>(ace.getValue())));
+ }
+ }
+
+ // find all ACEs that should be added but are not in the original ACE list
+ for (Map.Entry<String, Set<String>> ace : adds.entrySet()) {
+ if (!originals.containsKey(ace.getKey()) && !ace.getValue().isEmpty()) {
+ newACEs.add(new AccessControlEntryImpl(new AccessControlPrincipalDataImpl(ace.getKey()),
+ new ArrayList<String>(ace.getValue())));
+ }
+ }
+
+ return new AccessControlListImpl(newACEs);
+ }
+
+ /**
+ * Converts a list of ACEs into Map for better handling.
+ */
+ private Map<String, Set<String>> convertAclToMap(AccessControlList acl) {
+ Map<String, Set<String>> result = new HashMap<String, Set<String>>();
+
+ if ((acl == null) || (acl.getAces() == null)) {
+ return result;
+ }
+
+ for (AccessControlEntry ace : acl.getAces()) {
+ // don't consider indirect ACEs - we can't change them
+ if (!ace.isDirect()) {
+ // ignore
+ continue;
+ }
+
+ // although a principal must not be null, check it
+ if ((ace.getPrincipal() == null) || (ace.getPrincipal().getPrincipalId() == null)) {
+ // ignore
+ continue;
+ }
+
+ Set<String> permissions = new HashSet<String>();
+ if (ace.getPermissions() != null) {
+ permissions.addAll(ace.getPermissions());
+ }
+
+ result.put(ace.getPrincipal().getPrincipalId(), permissions);
+ }
+
+ return result;
+ }
+
+ /**
+ * Retrieves the Service Document from the server and caches the repository info objects,
+ * collections, links, URI templates, etc.
+ */
+ @SuppressWarnings("unchecked")
+ protected List<RepositoryInfoData> getRepositoriesInternal(String repositoryId) {
+ List<RepositoryInfoData> repInfos = new ArrayList<RepositoryInfoData>();
+
+ // retrieve service doc
+ UrlBuilder url = new UrlBuilder(getServiceDocURL());
+ url.addParameter(Constants.PARAM_REPOSITORY_ID, repositoryId);
+
+ // read and parse
+ HttpUtils.Response resp = read(url);
+ ServiceDoc serviceDoc = parse(resp.getStream(), ServiceDoc.class);
+
+ // walk through the workspaces
+ for (RepositoryWorkspace ws : serviceDoc.getWorkspaces()) {
+ if (ws.getId() == null) {
+ // found a non-CMIS workspace
+ continue;
+ }
+
+ for (AtomElement element : ws.getElements()) {
+ if (is(NAME_COLLECTION, element)) {
+ Map<String, String> colMap = (Map<String, String>) element.getObject();
+ addCollection(ws.getId(), colMap.get("collectionType"), colMap.get("href"));
+ }
+ else if (element.getObject() instanceof AtomLink) {
+ addRepositoryLink(ws.getId(), (AtomLink) element.getObject());
+ }
+ else if (is(NAME_URI_TEMPLATE, element)) {
+ Map<String, String> tempMap = (Map<String, String>) element.getObject();
+ addTemplate(ws.getId(), tempMap.get("type"), tempMap.get("template"));
+ }
+ else if (element.getObject() instanceof CmisRepositoryInfoType) {
+ repInfos.add(convert((CmisRepositoryInfoType) element.getObject()));
+ }
+ }
+ }
+
+ return repInfos;
+ }
+
+ /**
+ * Retrieves an object from the server and caches the links.
+ */
+ protected ObjectData getObjectInternal(String repositoryId, IdentifierType idOrPath,
+ String objectIdOrPath, ReturnVersion returnVersion, String filter,
+ Boolean includeAllowableActions, IncludeRelationships includeRelationships,
+ String renditionFilter, Boolean includePolicyIds, Boolean includeAcl, ExtensionsData extension) {
+ ObjectData result = null;
+
+ Map<String, Object> parameters = new HashMap<String, Object>();
+ parameters.put(Constants.PARAM_ID, objectIdOrPath);
+ parameters.put(Constants.PARAM_PATH, objectIdOrPath);
+ parameters.put(Constants.PARAM_RETURN_VERSION, returnVersion);
+ parameters.put(Constants.PARAM_FILTER, filter);
+ parameters.put(Constants.PARAM_ALLOWABLE_ACTIONS, includeAllowableActions);
+ parameters.put(Constants.PARAM_ACL, includeAcl);
+ parameters.put(Constants.PARAM_POLICY_IDS, includePolicyIds);
+ parameters.put(Constants.PARAM_RELATIONSHIPS, includeRelationships);
+ parameters.put(Constants.PARAM_RENDITION_FILTER, renditionFilter);
+
+ String link = loadTemplateLink(repositoryId,
+ (idOrPath == IdentifierType.ID ? Constants.TEMPLATE_OBJECT_BY_ID
+ : Constants.TEMPLATE_OBJECT_BY_PATH), parameters);
+ if (link == null) {
+ throw new CmisObjectNotFoundException("Unknown repository!");
+ }
+
+ UrlBuilder url = new UrlBuilder(link);
+ // workaround for missing template parameter in the CMIS spec
+ if ((returnVersion != null) && (returnVersion != ReturnVersion.THIS)) {
+ url.addParameter(Constants.PARAM_RETURN_VERSION, returnVersion);
+ }
+
+ // read and parse
+ HttpUtils.Response resp = read(url);
+ AtomEntry entry = parse(resp.getStream(), AtomEntry.class);
+
+ // we expect a CMIS entry
+ if (entry.getId() == null) {
+ throw new CmisConnectionException("Received Atom entry is not a CMIS entry!");
+ }
+
+ lockLinks();
+ try {
+ // clean up cache
+ removeLinks(repositoryId, entry.getId());
+
+ // walk through the entry
+ for (AtomElement element : entry.getElements()) {
+ if (element.getObject() instanceof AtomLink) {
+ addLink(repositoryId, entry.getId(), (AtomLink) element.getObject());
+ }
+ else if (element.getObject() instanceof CmisObjectType) {
+ result = convert((CmisObjectType) element.getObject());
+ }
+ }
+ }
+ finally {
+ unlockLinks();
+ }
+
+ return result;
+ }
+
+ /**
+ * Retrieves a type definition.
+ */
+ protected TypeDefinition getTypeDefinitionInternal(String repositoryId, String typeId) {
+ TypeDefinition result = null;
+
+ Map<String, Object> parameters = new HashMap<String, Object>();
+ parameters.put(Constants.PARAM_ID, typeId);
+
+ String link = loadTemplateLink(repositoryId, Constants.TEMPLATE_TYPE_BY_ID, parameters);
+ if (link == null) {
+ throw new CmisObjectNotFoundException("Unknown repository!");
+ }
+
+ // read and parse
+ HttpUtils.Response resp = read(new UrlBuilder(link));
+ AtomEntry entry = parse(resp.getStream(), AtomEntry.class);
+
+ // we expect a CMIS entry
+ if (entry.getId() == null) {
+ throw new CmisConnectionException("Received Atom entry is not a CMIS entry!");
+ }
+
+ lockTypeLinks();
+ try {
+ // clean up cache
+ removeTypeLinks(repositoryId, entry.getId());
+
+ // walk through the entry
+ for (AtomElement element : entry.getElements()) {
+ if (element.getObject() instanceof AtomLink) {
+ addTypeLink(repositoryId, entry.getId(), (AtomLink) element.getObject());
+ }
+ else if (element.getObject() instanceof CmisTypeDefinitionType) {
+ result = convert((CmisTypeDefinitionType) element.getObject());
+ }
+ }
+ }
+ finally {
+ unlockTypeLinks();
+ }
+
+ return result;
+ }
+
+ /**
+ * Updates the ACL of an object.
+ */
+ protected Acl updateAcl(String repositoryId, String objectId, AccessControlList acl,
+ AclPropagation aclPropagation) {
+
+ // find the link
+ String link = loadLink(repositoryId, objectId, Constants.REL_ACL, Constants.MEDIATYPE_ACL);
+
+ if (link == null) {
+ throwLinkException(repositoryId, objectId, Constants.REL_ACL, Constants.MEDIATYPE_ACL);
+ }
+
+ UrlBuilder aclUrl = new UrlBuilder(link);
+ aclUrl.addParameter(Constants.PARAM_ACL_PROPAGATION, aclPropagation);
+
+ // set up object and writer
+ final CmisAccessControlListType aclJaxb = convert(acl);
+
+ // update
+ HttpUtils.Response resp = put(aclUrl, Constants.MEDIATYPE_ACL, new HttpUtils.Output() {
+ public void write(OutputStream out) throws Exception {
+ JaxBHelper.marshal(JaxBHelper.CMIS_OBJECT_FACTORY.createAcl(aclJaxb), out, false);
+ }
+ });
+
+ // parse new entry
+ return parse(resp.getStream(), Acl.class);
+ }
+
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AbstractAtomPubService.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AbstractAtomPubService.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AbstractAtomPubService.java
------------------------------------------------------------------------------
svn:keywords = Id
Added: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AclServiceImpl.java
URL: http://svn.apache.org/viewvc/incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AclServiceImpl.java?rev=934361&view=auto
==============================================================================
--- incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AclServiceImpl.java (added)
+++ incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AclServiceImpl.java Thu Apr 15 10:33:49 2010
@@ -0,0 +1,105 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.chemistry.opencmis.client.bindings.spi.atompub;
+
+import static org.apache.chemistry.opencmis.commons.impl.Converter.convert;
+
+import org.apache.chemistry.opencmis.client.bindings.spi.Session;
+import org.apache.chemistry.opencmis.client.bindings.spi.atompub.objects.Acl;
+import org.apache.chemistry.opencmis.commons.api.ExtensionsData;
+import org.apache.chemistry.opencmis.commons.enums.AclPropagation;
+import org.apache.chemistry.opencmis.commons.impl.Constants;
+import org.apache.chemistry.opencmis.commons.impl.UrlBuilder;
+import org.apache.chemistry.opencmis.commons.provider.AccessControlList;
+import org.apache.chemistry.opencmis.commons.provider.AclService;
+
+/**
+ * ACL Service AtomPub client.
+ *
+ * @author <a href="mailto:fmueller@opentext.com">Florian Müller</a>
+ *
+ */
+public class AclServiceImpl extends AbstractAtomPubService implements AclService {
+
+ /**
+ * Constructor.
+ */
+ public AclServiceImpl(Session session) {
+ setSession(session);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.apache.opencmis.client.provider.ACLService#applyACL(java.lang.String,
+ * java.lang.String, org.apache.opencmis.client.provider.AccessControlList,
+ * org.apache.opencmis.client.provider.AccessControlList,
+ * org.apache.opencmis.commons.enums.ACLPropagation,
+ * org.apache.opencmis.client.provider.ExtensionsData)
+ */
+ public AccessControlList applyAcl(String repositoryId, String objectId,
+ AccessControlList addAces, AccessControlList removeAces, AclPropagation aclPropagation,
+ ExtensionsData extension) {
+ AccessControlList result = null;
+
+ // fetch the current ACL
+ AccessControlList originalAces = getAcl(repositoryId, objectId, false, null);
+
+ // if no changes required, just return the ACL
+ if (!isAclMergeRequired(addAces, removeAces)) {
+ return originalAces;
+ }
+
+ // merge ACLs
+ AccessControlList newACL = mergeAcls(originalAces, addAces, removeAces);
+
+ // update ACL
+ Acl acl = updateAcl(repositoryId, objectId, newACL, aclPropagation);
+ result = convert(acl.getACL(), null);
+
+ return result;
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see org.apache.opencmis.client.provider.ACLService#getACL(java.lang.String, java.lang.String,
+ * java.lang.Boolean, org.apache.opencmis.client.provider.ExtensionsData)
+ */
+ public AccessControlList getAcl(String repositoryId, String objectId,
+ Boolean onlyBasicPermissions, ExtensionsData extension) {
+
+ // find the link
+ String link = loadLink(repositoryId, objectId, Constants.REL_ACL, Constants.MEDIATYPE_ACL);
+
+ if (link == null) {
+ throwLinkException(repositoryId, objectId, Constants.REL_ACL, Constants.MEDIATYPE_ACL);
+ }
+
+ UrlBuilder url = new UrlBuilder(link);
+ url.addParameter(Constants.PARAM_ONLY_BASIC_PERMISSIONS, onlyBasicPermissions);
+
+ // read and parse
+ HttpUtils.Response resp = read(url);
+ Acl acl = parse(resp.getStream(), Acl.class);
+
+ return convert(acl.getACL(), null);
+ }
+
+}
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AclServiceImpl.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AclServiceImpl.java
------------------------------------------------------------------------------
svn:executable = *
Propchange: incubator/chemistry/opencmis/trunk/chemistry-opencmis-client/chemistry-opencmis-client-bindings/src/main/java/org/apache/chemistry/opencmis/client/bindings/spi/atompub/AclServiceImpl.java
------------------------------------------------------------------------------
svn:keywords = Id