2 * This document is a part of the source code and related artifacts
3 * for CollectionSpace, an open source collections management system
4 * for museums and related institutions:
6 * http://www.collectionspace.org
7 * http://wiki.collectionspace.org
9 * Copyright 2009 University of California at Berkeley
11 * Licensed under the Educational Community License (ECL), Version 2.0.
12 * You may not use this file except in compliance with this License.
14 * You may obtain a copy of the ECL 2.0 License at
16 * https://source.collectionspace.org/collection-space/LICENSE.txt
18 * Unless required by applicable law or agreed to in writing, software
19 * distributed under the License is distributed on an "AS IS" BASIS,
20 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
21 * See the License for the specific language governing permissions and
22 * limitations under the License.
24 package org.collectionspace.services.common.context;
26 import java.util.ArrayList;
27 import java.util.HashMap;
28 import java.util.List;
30 import java.util.Properties;
32 import javax.ws.rs.core.MultivaluedMap;
33 import javax.ws.rs.core.UriInfo;
35 import org.collectionspace.authentication.spi.AuthNContext;
36 import org.collectionspace.services.client.AuthorityClient;
37 import org.collectionspace.services.client.CollectionSpaceClient;
38 import org.collectionspace.services.client.IClientQueryParams;
39 import org.collectionspace.services.client.IQueryManager;
40 import org.collectionspace.services.client.workflow.WorkflowClient;
41 import org.collectionspace.services.common.ServiceMain;
42 import org.collectionspace.services.common.api.Tools;
43 import org.collectionspace.services.common.authorization_mgt.AuthorizationCommon;
44 import org.collectionspace.services.common.config.PropertyItemUtils;
45 import org.collectionspace.services.common.config.ServiceConfigUtils;
46 import org.collectionspace.services.common.config.TenantBindingConfigReaderImpl;
47 import org.collectionspace.services.common.document.DocumentHandler;
48 import org.collectionspace.services.common.document.DocumentFilter;
49 import org.collectionspace.services.common.document.ValidatorHandler;
50 import org.collectionspace.services.common.security.SecurityContext;
51 import org.collectionspace.services.common.security.SecurityContextImpl;
52 import org.collectionspace.services.common.security.UnauthorizedException;
53 import org.collectionspace.services.config.ClientType;
54 import org.collectionspace.services.config.service.ObjectPartType;
55 import org.collectionspace.services.config.service.ServiceBindingType;
56 import org.collectionspace.services.config.tenant.RemoteClientConfig;
57 import org.collectionspace.services.config.tenant.RepositoryDomainType;
58 import org.collectionspace.services.config.tenant.TenantBindingType;
59 import org.collectionspace.services.config.types.PropertyItemType;
60 import org.collectionspace.services.config.types.PropertyType;
61 import org.slf4j.Logger;
62 import org.slf4j.LoggerFactory;
65 * AbstractServiceContext
67 * $LastChangedRevision: $
82 @SuppressWarnings("rawtypes")
83 public abstract class AbstractServiceContextImpl<IT, OT>
84 implements ServiceContext<IT, OT> {
87 final Logger logger = LoggerFactory.getLogger(AbstractServiceContextImpl.class);
89 /** The properties. */
90 Map<String, Object> properties = new HashMap<String, Object>();
91 /** The object part map. */
92 Map<String, ObjectPartType> objectPartMap = new HashMap<String, ObjectPartType>();
93 /** The service binding. */
94 protected ServiceBindingType serviceBinding;
95 /** The tenant binding. */
96 private TenantBindingType tenantBinding;
97 /** repository domain used by the service */
98 private RepositoryDomainType repositoryDomain;
99 /** The override document type. */
100 private String overrideDocumentType = null;
101 /** The val handlers. */
102 private List<ValidatorHandler<IT, OT>> valHandlers = null;
103 /** The authority client -use for shared authority server */
104 private AuthorityClient authorityClient = null;
105 /** The doc handler. */
106 private DocumentHandler docHandler = null;
107 /** security context */
108 private SecurityContext securityContext;
109 /** The sessions JAX-RS URI information */
110 private UriInfo uriInfo;
111 /** The current repository session */
112 private Object currentRepositorySession;
113 /** A reference count for the current repository session */
114 private int currentRepoSesssionRefCount = 0;
117 * Instantiates a new abstract service context impl.
119 private AbstractServiceContextImpl() {
120 // private constructor for singleton pattern
122 // request query params
123 /** The query params. */
124 private MultivaluedMap<String, String> queryParams;
127 * Instantiates a new abstract service context impl.
129 * @param serviceName the service name
131 * @throws UnauthorizedException the unauthorized exception
133 protected AbstractServiceContextImpl(String serviceName, UriInfo uriInfo) throws UnauthorizedException {
135 //establish security context
136 securityContext = new SecurityContextImpl(uriInfo);
137 //make sure tenant context exists
138 checkTenantContext();
140 String tenantId = securityContext.getCurrentTenantId();
141 if (AuthorizationCommon.ALL_TENANTS_MANAGER_TENANT_ID.equals(tenantId) ||
142 AuthNContext.ANONYMOUS_TENANT_ID.equals(tenantId)) {
143 // Tenant Manager has no tenant binding, so don't bother...
144 tenantBinding = null;
145 serviceBinding = null;
146 repositoryDomain = null;
148 //retrieve service bindings
149 TenantBindingConfigReaderImpl tReader =
150 ServiceMain.getInstance().getTenantBindingConfigReader();
151 tenantBinding = tReader.getTenantBinding(tenantId);
152 if (tenantBinding == null) {
153 String msg = "No tenant binding found for tenantId=" + tenantId
154 + " while processing request for service= " + serviceName;
156 throw new IllegalStateException(msg);
158 serviceBinding = tReader.getServiceBinding(tenantId, serviceName);
159 if (serviceBinding == null) {
160 String msg = "No service binding found while processing request for "
161 + serviceName + " for tenant id=" + getTenantId()
162 + " name=" + getTenantName();
164 throw new IllegalStateException(msg);
166 if (logger.isDebugEnabled()) {
167 logger.debug("tenantId=" + tenantId
168 + " service binding=" + serviceBinding.getName());
170 repositoryDomain = tReader.getRepositoryDomain(tenantId, serviceName);
171 if (repositoryDomain != null) {
172 if (logger.isDebugEnabled()) {
173 logger.debug("tenantId=" + tenantId
174 + " repository doamin=" + repositoryDomain.getName());
180 public int getTimeoutParam(UriInfo ui) {
181 int result = DEFAULT_TX_TIMEOUT;
183 MultivaluedMap<String, String> queryParams = (ui == null) ? null : ui.getQueryParameters();
184 if (queryParams != null) {
185 String timeoutString = queryParams.getFirst(IClientQueryParams.IMPORT_TIMEOUT_PARAM);
186 if (timeoutString != null)
188 result = Integer.parseInt(timeoutString);
189 } catch (NumberFormatException e) {
190 logger.warn("Transaction timeout period parameter could not be parsed. The characters in the parameter string must all be decimal digits. The Import service will use the default timeout period instead.",
199 public int getTimeoutSecs() {
200 UriInfo uriInfo = this.getUriInfo();
201 return this.getTimeoutParam(uriInfo);
205 * Returns TRUE unless the "recordUpdates" query param is set with a value of either "false", "FALSE", or "0"
209 public boolean shouldUpdateCoreValues() {
210 boolean recordUpdates = true;
212 MultivaluedMap<String, String> queryParams = getQueryParams();
213 String paramValue = queryParams.getFirst(IClientQueryParams.UPDATE_CORE_VALUES);
214 if (paramValue != null && paramValue.equalsIgnoreCase(Boolean.FALSE.toString())) { // Find our if the caller wants us to record updates
215 recordUpdates = false;
216 } else if (paramValue != null && paramValue.equals(Long.toString(0))) {
217 recordUpdates = false;
220 return recordUpdates;
224 * Default value is 'FALSE'
225 * If this returns true, it means that the refname values in referencing objects (records that reference authority or vocabulary terms) will be updated
226 * regardless of their current value. This is sometimes needed when refname values become stale for one of several reasons.
230 public boolean shouldForceUpdateRefnameReferences() {
231 boolean forceUpdates = false;
233 MultivaluedMap<String, String> queryParams = getQueryParams();
234 String paramValue = queryParams.getFirst(IClientQueryParams.FORCE_REFNAME_UPDATES);
235 if (paramValue != null && paramValue.equalsIgnoreCase(Boolean.TRUE.toString())) { // Find our if the caller wants us to force refname updates
237 } else if (paramValue != null && paramValue.equals(Long.toString(1))) {
246 * @see org.collectionspace.services.common.context.ServiceContext#getCommonPartLabel()
249 public String getCommonPartLabel() {
250 return getCommonPartLabel(getServiceName());
254 * @see org.collectionspace.services.common.context.ServiceContext#getCommonPartLabel(java.lang.String)
256 public String getCommonPartLabel(String schemaName) {
257 return schemaName.toLowerCase() + PART_LABEL_SEPARATOR + PART_COMMON_LABEL;
261 * @see org.collectionspace.services.common.context.ServiceContext#getPartsMetadata()
264 public Map<String, ObjectPartType> getPartsMetadata() {
265 if (objectPartMap.size() != 0) {
266 return objectPartMap;
268 ServiceBindingUtils.getPartsMetadata(getServiceBinding(), objectPartMap);
269 return objectPartMap;
273 * Gets the properties for part.
275 * @param partLabel the part label
277 * @return the properties for part
279 public List<PropertyItemType> getPropertiesForPart(String partLabel) {
280 Map<String, ObjectPartType> partMap = getPartsMetadata();
281 ObjectPartType part = partMap.get(partLabel);
283 throw new RuntimeException("No such part found: " + partLabel);
285 List<PropertyType> propNodeList = part.getProperties();
286 return propNodeList.isEmpty() ? null : propNodeList.get(0).getItem();
290 * @param partLabel The name of the scehma part to search in
291 * @param propName The name of the property (or properties) to find
292 * @param qualified Whether the returned values should be qualified with the
293 * partLabel. This is when the property values are schema field references.
294 * @return List of property values for the matched property on the named schema part.
296 public List<String> getPropertyValuesForPart(String partLabel, String propName, boolean qualified) {
297 List<PropertyItemType> allProps = getPropertiesForPart(partLabel);
298 return PropertyItemUtils.getPropertyValuesByName(allProps, propName,
299 (qualified ? (partLabel + ":") : null));
303 * @param propName The name of the property (or properties) to find
304 * @param qualified Whether the returned values should be qualified with the
305 * partLabel. This is when the property values are schema field references.
306 * @return List of property values for the matched property on any schema part.
308 public List<String> getAllPartsPropertyValues(String propName, boolean qualified) {
309 return ServiceBindingUtils.getAllPartsPropertyValues(getServiceBinding(), propName, qualified);
313 * @see org.collectionspace.services.common.context.ServiceContext#getServiceBindingPropertyValue(java.lang.String)
315 public String getServiceBindingPropertyValue(String propName) {
316 return ServiceBindingUtils.getPropertyValue(getServiceBinding(), propName);
320 * Gets the common part properties.
322 * @return the common part properties
324 public List<PropertyItemType> getCommonPartProperties() {
325 return getPropertiesForPart(getCommonPartLabel());
329 * @param propName The name of the property (or properties) to find
330 * @param qualified Whether the returned values should be qualified with the
331 * partLabel. This is when the property values are schema field references.
332 * @return List of property values for the matched property on the common schema part.
334 public List<String> getCommonPartPropertyValues(String propName, boolean qualified) {
335 return getPropertyValuesForPart(getCommonPartLabel(), propName, qualified);
339 * @see org.collectionspace.services.common.context.ServiceContext#getQualifiedServiceName()
342 public String getQualifiedServiceName() {
343 return TenantBindingConfigReaderImpl.getTenantQualifiedServiceName(getTenantId(), getServiceName());
347 * @see org.collectionspace.services.common.context.ServiceContext#getRepositoryClientName()
350 public String getRepositoryClientName() {
351 if (repositoryDomain == null) {
354 return repositoryDomain.getRepositoryClient();
358 * @see org.collectionspace.services.common.context.ServiceContext#getRepositoryClientType()
361 public ClientType getRepositoryClientType() {
362 //assumption: there is only one repository client configured
363 return ServiceMain.getInstance().getClientType();
367 * @see org.collectionspace.services.common.context.ServiceContext#getRepositoryDomainName()
370 public String getRepositoryDomainName() {
371 if (repositoryDomain == null) {
374 return repositoryDomain.getName();
378 * @see org.collectionspace.services.common.context.ServiceContext#getRepositoryDomainName()
381 public String getRepositoryDomainStorageName() {
382 if (repositoryDomain == null) {
385 return repositoryDomain.getStorageName();
389 * @see org.collectionspace.services.common.context.ServiceContext#getRepositoryWorkspaceId()
392 public String getRepositoryWorkspaceId() {
393 return ServiceMain.getInstance().getWorkspaceId(getTenantId(), getServiceName());
397 * @see org.collectionspace.services.common.context.ServiceContext#getRepositoryWorkspaceName()
400 public String getRepositoryWorkspaceName() {
401 //service name is workspace name by convention
402 return serviceBinding.getName();
406 * @see org.collectionspace.services.common.context.ServiceContext#getServiceBinding()
409 public ServiceBindingType getServiceBinding() {
410 return serviceBinding;
414 * @see org.collectionspace.services.common.context.ServiceContext#getServiceName()
417 public String getServiceName() {
418 return serviceBinding.getName();
422 * @see org.collectionspace.services.common.context.ServiceContext#getDocumentType()
425 public String getDocumentType() {
426 // If they have not overridden the setting, use the type of the service
428 return (overrideDocumentType != null) ? overrideDocumentType : serviceBinding.getObject().getName();
432 public String getTenantQualifiedDoctype(String docType) {
433 // If they have not overridden the setting, use the type of the service
435 String result = ServiceBindingUtils.getTenantQualifiedDocType(this.getTenantId(), docType);
441 public String getTenantQualifiedDoctype() {
442 String docType = (overrideDocumentType != null) ? overrideDocumentType : serviceBinding.getObject().getName();
443 return getTenantQualifiedDoctype(docType);
447 * @see org.collectionspace.services.common.context.ServiceContext#setDocumentType(java.lang.String)
450 public void setDocumentType(String docType) {
451 overrideDocumentType = docType;
455 * @see org.collectionspace.services.common.context.ServiceContext#getSecurityContext()
458 public SecurityContext getSecurityContext() {
459 return securityContext;
463 * @see org.collectionspace.services.common.context.ServiceContext#getUserId()
466 public String getUserId() {
467 return securityContext.getUserId();
471 * @see org.collectionspace.services.common.context.ServiceContext#getTenantId()
474 public String getTenantId() {
475 return securityContext.getCurrentTenantId();
479 * @see org.collectionspace.services.common.context.ServiceContext#getTenantName()
482 public String getTenantName() {
483 return securityContext.getCurrentTenantName();
487 * @see org.collectionspace.services.common.context.ServiceContext#getInput()
490 public abstract IT getInput();
493 * @see org.collectionspace.services.common.context.ServiceContext#setInput(java.lang.Object)
496 public abstract void setInput(IT input);
499 * @see org.collectionspace.services.common.context.ServiceContext#getOutput()
502 public abstract OT getOutput();
505 * @see org.collectionspace.services.common.context.ServiceContext#setOutput(java.lang.Object)
508 public abstract void setOutput(OT output);
511 * @see org.collectionspace.services.common.context.ServiceContext#getProperties()
514 public Map<String, Object> getProperties() {
519 * @see org.collectionspace.services.common.context.ServiceContext#setProperties(java.util.Map)
522 public void setProperties(Map<String, Object> props) {
523 properties.putAll(props);
527 * @see org.collectionspace.services.common.context.ServiceContext#getProperty(java.lang.String)
529 public Object getProperty(String name) {
530 return properties.get(name);
534 * @see org.collectionspace.services.common.context.ServiceContext#setProperty(java.lang.String, java.lang.Object)
536 public void setProperty(String name, Object o) {
537 properties.put(name, o);
541 * checkTenantContext makss sure tenant context exists
545 * @throws UnauthorizedException the unauthorized exception
547 private void checkTenantContext() throws UnauthorizedException {
549 String tenantId = securityContext.getCurrentTenantId();
550 if (tenantId == null) {
551 String msg = "Could not find tenant context";
553 throw new UnauthorizedException(msg);
558 * Helps to filter for queries that either want to include or exclude documents in deleted workflow states.
563 private static String buildWorkflowWhereClause(MultivaluedMap<String, String> queryParams) {
564 String result = null;
566 String includeDeleted = queryParams.getFirst(WorkflowClient.WORKFLOW_QUERY_NONDELETED);
567 String includeOnlyDeleted = queryParams.getFirst(WorkflowClient.WORKFLOW_QUERY_ONLY_DELETED);
569 if (includeDeleted != null && includeDeleted.equalsIgnoreCase(Boolean.FALSE.toString())) {
570 result = String.format("(ecm:currentLifeCycleState <> '%s' AND ecm:currentLifeCycleState <> '%s' AND ecm:currentLifeCycleState <> '%s')",
571 WorkflowClient.WORKFLOWSTATE_DELETED, WorkflowClient.WORKFLOWSTATE_LOCKED_DELETED, WorkflowClient.WORKFLOWSTATE_REPLICATED_DELETED);
572 } else if (includeOnlyDeleted != null && includeOnlyDeleted.equalsIgnoreCase(Boolean.TRUE.toString())) {
573 result = String.format("(ecm:currentLifeCycleState <> '%s' AND ecm:currentLifeCycleState <> '%s' AND ecm:currentLifeCycleState <> '%s')",
574 WorkflowClient.WORKFLOWSTATE_PROJECT, WorkflowClient.WORKFLOWSTATE_LOCKED, WorkflowClient.WORKFLOWSTATE_REPLICATED);
581 * Creates the document handler instance.
583 * @return the document handler
585 * @throws Exception the exception
587 private DocumentHandler createDocumentHandlerInstance() throws Exception {
588 docHandler = ServiceConfigUtils.createDocumentHandlerInstance(tenantBinding, serviceBinding);
590 // Create a default document filter
592 docHandler.setServiceContext(this);
593 DocumentFilter docFilter = docHandler.createDocumentFilter();
595 // If the context was created with query parameters,
596 // reflect the values of those parameters in the document filter
597 // to specify sort ordering, pagination, etc.
599 MultivaluedMap<String, String> queryParameters = this.getQueryParams();
600 if (queryParameters != null) {
601 docFilter.setSortOrder(queryParameters);
602 docFilter.setPagination(queryParameters);
603 String workflowWhereClause = buildWorkflowWhereClause(queryParameters);
604 if (workflowWhereClause != null) {
605 docFilter.appendWhereClause(workflowWhereClause, IQueryManager.SEARCH_QUALIFIER_AND);
609 docHandler.setDocumentFilter(docFilter);
615 * @see org.collectionspace.services.common.context.ServiceContext#getDocumentHandler()
618 public DocumentHandler getDocumentHandler() throws Exception {
619 DocumentHandler result = docHandler;
620 // create a new instance if one does not yet exist
621 if (result == null) {
622 result = createDocumentHandlerInstance();
628 public void setDocumentHandler(DocumentHandler handler) throws Exception {
629 if (handler != null) {
630 docHandler = handler;
635 * @see org.collectionspace.services.common.context.ServiceContext#getDocumentHanlder(javax.ws.rs.core.MultivaluedMap)
638 public DocumentHandler getDocumentHandler(MultivaluedMap<String, String> queryParams) throws Exception {
639 DocumentHandler result = getDocumentHandler();
640 DocumentFilter documentFilter = result.getDocumentFilter(); //to see results in debugger variables view
641 documentFilter.setPagination(queryParams);
646 * If this element is set in the service binding then use it otherwise
647 * assume that asserts are NOT disabled.
649 private boolean disableValidationAsserts() {
651 Boolean disableAsserts = getServiceBinding().isDisableAsserts();
652 result = (disableAsserts != null) ? disableAsserts : false;
657 * @see org.collectionspace.services.common.context.ServiceContext#getValidatorHandlers()
660 public List<ValidatorHandler<IT, OT>> getValidatorHandlers() throws Exception {
661 if (valHandlers != null) {
664 List<String> handlerClazzes = getServiceBinding().getValidatorHandler();
665 List<ValidatorHandler<IT, OT>> handlers = new ArrayList<ValidatorHandler<IT, OT>>(handlerClazzes.size());
666 ClassLoader tccl = Thread.currentThread().getContextClassLoader();
667 for (String clazz : handlerClazzes) {
668 clazz = clazz.trim();
670 Class<?> c = tccl.loadClass(clazz);
671 if (disableValidationAsserts() == false) {
672 // enable validation assertions
673 tccl.setClassAssertionStatus(clazz, true);
675 if (ValidatorHandler.class.isAssignableFrom(c)) {
676 handlers.add((ValidatorHandler) c.newInstance());
678 } catch (ClassNotFoundException e) {
679 String msg = String.format("Missing document validation handler: '%s'.", clazz);
681 logger.trace(msg, e);
684 valHandlers = handlers;
689 * If one doesn't already exist, use the default properties filename to load a set of properties that
690 * will be used to create an HTTP client to a CollectionSpace instance.
693 public AuthorityClient getClient() throws Exception {
694 AuthorityClient result = authorityClient;
696 if (authorityClient == null) {
697 result = authorityClient = getClient(CollectionSpaceClient.DEFAULT_CLIENT_PROPERTIES_FILENAME);
704 * Use the properties filename passed in to load the URL and credentials that will be used
705 * to create a new HTTP client.
707 * Never uses or resets the this.authorityClient member. Always creates a new HTTP client using
708 * the loaded properties.
711 * @see org.collectionspace.services.common.context.ServiceContext#getClient(java.lang.String)
714 public AuthorityClient getClient(String clientPropertiesFilename) throws Exception {
715 AuthorityClient result = null;
717 Properties inProperties = Tools.loadProperties(clientPropertiesFilename, true);
718 result = getClient(inProperties);
723 public AuthorityClient getClient(Properties inProperties) throws Exception {
724 AuthorityClient result = null;
726 String authorityClientClazz = getServiceBinding().getClientHandler();
727 ClassLoader tccl = Thread.currentThread().getContextClassLoader();
728 authorityClientClazz = authorityClientClazz.trim();
730 Class<?> c = tccl.loadClass(authorityClientClazz);
731 if (AuthorityClient.class.isAssignableFrom(c)) {
732 result = authorityClient = ((AuthorityClient) c.newInstance());
733 result.setClientProperties(inProperties);
735 logger.error(String.format("The service binding clientHandler class '%s' for '%s' service was not of type AuthorityClient.",
736 authorityClientClazz, this.getServiceName()));
738 } catch (ClassNotFoundException e) {
739 String msg = String.format("Missing document validation handler: '%s'.", authorityClientClazz);
741 logger.trace(msg, e);
748 public AuthorityClient getClient(RemoteClientConfig remoteClientConfig) throws Exception {
749 AuthorityClient result = null;
751 Properties properties = new Properties();
752 properties.setProperty(AuthorityClient.URL_PROPERTY, remoteClientConfig.getUrl());
753 properties.setProperty(AuthorityClient.USER_PROPERTY, remoteClientConfig.getUser());
754 properties.setProperty(AuthorityClient.PASSWORD_PROPERTY, remoteClientConfig.getPassword());
755 properties.setProperty(AuthorityClient.SSL_PROPERTY, remoteClientConfig.getSsl());
756 properties.setProperty(AuthorityClient.AUTH_PROPERTY, remoteClientConfig.getAuth());
759 String tenantId = remoteClientConfig.getTenantId();
760 if (tenantId != null) {
761 properties.setProperty(AuthorityClient.TENANT_ID_PROPERTY, tenantId);
763 String tenantName = remoteClientConfig.getTenantName();
764 if (tenantName != null) {
765 properties.setProperty(AuthorityClient.TENANT_NAME_PROPERTY, tenantName);
768 result = getClient(properties);
774 public void addValidatorHandler(ValidatorHandler<IT, OT> validator) throws Exception {
775 if (valHandlers == null) {
776 valHandlers = new ArrayList<ValidatorHandler<IT, OT>>();
778 valHandlers.add(validator);
782 * @see java.lang.Object#toString()
785 public String toString() {
786 StringBuilder msg = new StringBuilder();
787 msg.append("AbstractServiceContext [");
788 msg.append("service name=" + serviceBinding.getName() + " ");
789 msg.append("service version=" + serviceBinding.getVersion() + " ");
790 msg.append("tenant id=" + tenantBinding.getId() + " ");
791 msg.append("tenant name=" + tenantBinding.getName() + " ");
792 msg.append(tenantBinding.getDisplayName() + " ");
793 if (repositoryDomain != null) {
794 msg.append("tenant repository domain=" + repositoryDomain.getName());
796 for (Map.Entry<String, Object> entry : properties.entrySet()) {
797 msg.append("property name=" + entry.getKey() + " value=" + entry.getValue().toString());
800 return msg.toString();
804 * @see org.collectionspace.services.common.context.ServiceContext#getQueryParams()
806 * When we first created these services, the RESTEasy query parameters used to be a modifiable map. That changed in a
807 * more recent version of RESTEasy, so we need to make a copy of the params into a modifiable map and return it instead.
810 public MultivaluedMap<String, String> getQueryParams() {
812 if (queryParams == null){
813 if (this.uriInfo != null){
814 queryParams = this.uriInfo.getQueryParameters();
817 if (queryParams == null){
818 queryParams = new org.jboss.resteasy.specimpl.MultivaluedMapImpl<String,String>();
820 return this.queryParams;
824 public MultivaluedMap<String, String> getQueryParamsPtr() {
825 return this.queryParams;
829 * @see org.collectionspace.services.common.context.ServiceContext#setQueryParams(javax.ws.rs.core.MultivaluedMap)
832 public void setQueryParams(MultivaluedMap<String, String> theQueryParams) {
833 this.queryParams = theQueryParams;
837 public void setUriInfo(UriInfo ui){
842 public UriInfo getUriInfo() {
847 * We expect the 'currentRepositorySession' member to be set only once per instance. Also, we expect only one open repository session
848 * per HTTP request. We'll log an error if we see more than one attempt to set a service context's current repo session.
850 * @see org.collectionspace.services.common.context.ServiceContext#setCurrentRepositorySession(java.lang.Object)
853 public void setCurrentRepositorySession(Object repoSession) throws Exception {
854 if (repoSession == null) {
855 String errMsg = "Setting a service context's repository session to null is not allowed.";
856 logger.error(errMsg);
857 throw new Exception(errMsg);
858 } else if (currentRepositorySession != null && currentRepositorySession != repoSession) {
859 String errMsg = "The current service context's repository session was replaced. This may cause unexpected behavior and/or data loss.";
860 logger.error(errMsg);
861 throw new Exception(errMsg);
864 currentRepositorySession = repoSession;
865 this.currentRepoSesssionRefCount++;
869 public void clearCurrentRepositorySession() {
870 if (this.currentRepoSesssionRefCount > 0) {
871 currentRepoSesssionRefCount--;
874 if (currentRepoSesssionRefCount == 0) {
875 this.currentRepositorySession = null;
880 public Object getCurrentRepositorySession() {
881 // TODO Auto-generated method stub
882 return currentRepositorySession;
886 public RepositoryDomainType getRepositoryDomain() {
887 return repositoryDomain;
891 public void setRepositoryDomain(RepositoryDomainType repositoryDomain) {
892 this.repositoryDomain = repositoryDomain;
896 * Check for a query parameter that indicates if we should force a sync even if the revision numbers indicate otherwise.
900 public boolean shouldForceSync() {
901 boolean forceSync = false;
903 MultivaluedMap<String, String> queryParams = getQueryParams();
904 String paramValue = queryParams.getFirst(IClientQueryParams.FORCE_SYCN);
905 if (paramValue != null && paramValue.equalsIgnoreCase(Boolean.TRUE.toString())) { // Find our if the caller wants us to force refname updates
907 } else if (paramValue != null && paramValue.equals(Long.toString(1))) {