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 package org.collectionspace.services.nuxeo.client.java;
20 import java.util.Hashtable;
21 import java.util.UUID;
22 import java.util.List;
24 import org.collectionspace.services.common.context.ServiceContext;
26 import org.collectionspace.services.common.document.BadRequestException;
27 import org.collectionspace.services.common.document.DocumentException;
28 import org.collectionspace.services.common.document.DocumentFilter;
29 import org.collectionspace.services.common.document.DocumentHandler;
30 import org.collectionspace.services.common.document.DocumentNotFoundException;
31 import org.collectionspace.services.common.document.DocumentHandler.Action;
32 import org.collectionspace.services.common.document.DocumentWrapper;
33 import org.collectionspace.services.common.document.DocumentWrapperImpl;
35 import org.collectionspace.services.nuxeo.util.NuxeoUtils;
36 import org.collectionspace.services.common.query.IQueryManager;
37 import org.collectionspace.services.common.repository.RepositoryClient;
39 import org.jboss.resteasy.plugins.providers.multipart.MultipartInput;
40 import org.jboss.resteasy.plugins.providers.multipart.MultipartOutput;
41 import org.nuxeo.common.utils.IdUtils;
42 import org.nuxeo.ecm.core.api.ClientException;
43 import org.nuxeo.ecm.core.api.DocumentModel;
44 import org.nuxeo.ecm.core.api.DocumentModelList;
45 import org.nuxeo.ecm.core.api.impl.DocumentModelListImpl;
46 import org.nuxeo.ecm.core.api.DocumentRef;
47 import org.nuxeo.ecm.core.api.IdRef;
48 import org.nuxeo.ecm.core.api.PathRef;
49 import org.nuxeo.ecm.core.api.repository.RepositoryInstance;
50 import org.nuxeo.ecm.core.client.NuxeoClient;
52 import org.slf4j.Logger;
53 import org.slf4j.LoggerFactory;
56 * RepositoryJavaClient is used to perform CRUD operations on documents in Nuxeo
57 * repository using Remote Java APIs. It uses @see DocumentHandler as IOHandler
60 * $LastChangedRevision: $ $LastChangedDate: $
62 public class RepositoryJavaClientImpl implements RepositoryClient {
65 * The Class QueryContext.
67 private class QueryContext {
71 /** The doc filter. */
72 DocumentFilter docFilter;
73 /** The where clause. */
81 * Instantiates a new query context.
84 * @throws DocumentNotFoundException the document not found exception
85 * @throws DocumentException the document exception
87 QueryContext(ServiceContext<MultipartInput, MultipartOutput> ctx) throws DocumentNotFoundException, DocumentException {
88 docType = ctx.getDocumentType();
89 if (docType == null) {
90 throw new DocumentNotFoundException(
91 "Unable to find DocumentType for service " + ctx.getServiceName());
93 domain = ctx.getRepositoryDomainName();
95 throw new DocumentNotFoundException(
96 "Unable to find Domain for service " + ctx.getServiceName());
98 tenantId = ctx.getTenantId();
99 if (tenantId == null) {
100 throw new IllegalArgumentException(
101 "Service context has no Tenant ID specified.");
106 * Instantiates a new query context.
109 * @param theWhereClause the the where clause
110 * @throws DocumentNotFoundException the document not found exception
111 * @throws DocumentException the document exception
113 QueryContext(ServiceContext<MultipartInput, MultipartOutput> ctx,
114 String theWhereClause) throws DocumentNotFoundException, DocumentException {
116 whereClause = theWhereClause;
120 * Instantiates a new query context.
123 * @param handler the handler
124 * @throws DocumentNotFoundException the document not found exception
125 * @throws DocumentException the document exception
127 QueryContext(ServiceContext<MultipartInput, MultipartOutput> ctx,
128 DocumentHandler handler) throws DocumentNotFoundException, DocumentException {
130 if (handler == null) {
131 throw new IllegalArgumentException(
132 "Document handler is missing.");
134 docFilter = handler.getDocumentFilter();
135 if (docFilter == null) {
136 throw new IllegalArgumentException(
137 "Document handler has no Filter specified.");
139 whereClause = docFilter.getWhereClause();
143 private final Logger logger = LoggerFactory.getLogger(RepositoryJavaClientImpl.class);
146 * Instantiates a new repository java client impl.
148 public RepositoryJavaClientImpl() {
153 * Sets the collection space core values.
156 * @param documentModel the document model
157 * @throws ClientException the client exception
159 private void setCollectionSpaceCoreValues(ServiceContext<MultipartInput, MultipartOutput> ctx,
160 DocumentModel documentModel,
161 Action action) throws ClientException {
163 // Add the tenant ID value to the new entity
165 documentModel.setProperty(DocumentModelHandler.COLLECTIONSPACE_CORE_SCHEMA,
166 DocumentModelHandler.COLLECTIONSPACE_CORE_TENANTID,
170 //add creation date value
180 * create document in the Nuxeo repository
182 * @param ctx service context under which this method is invoked
184 * of the document created
186 * should be used by the caller to provide and transform the
188 * @return id in repository of the newly created document
189 * @throws DocumentException
192 public String create(ServiceContext ctx,
193 DocumentHandler handler) throws BadRequestException,
196 if (ctx.getDocumentType() == null) {
197 throw new IllegalArgumentException(
198 "RepositoryJavaClient.create: docType is missing");
200 if (handler == null) {
201 throw new IllegalArgumentException(
202 "RepositoryJavaClient.create: handler is missing");
204 String nuxeoWspaceId = ctx.getRepositoryWorkspaceId();
205 if (nuxeoWspaceId == null) {
206 throw new DocumentNotFoundException(
207 "Unable to find workspace for service " + ctx.getServiceName()
208 + " check if the workspace exists in the Nuxeo repository");
210 RepositoryInstance repoSession = null;
212 handler.prepare(Action.CREATE);
213 repoSession = getRepositorySession();
214 DocumentRef nuxeoWspace = new IdRef(nuxeoWspaceId);
215 DocumentModel wspaceDoc = repoSession.getDocument(nuxeoWspace);
216 String wspacePath = wspaceDoc.getPathAsString();
217 //give our own ID so PathRef could be constructed later on
218 String id = IdUtils.generateId(UUID.randomUUID().toString());
219 // create document model
220 DocumentModel doc = repoSession.createDocumentModel(wspacePath, id,
221 ctx.getDocumentType());
222 ((DocumentModelHandler) handler).setRepositorySession(repoSession);
223 DocumentWrapper<DocumentModel> wrapDoc = new DocumentWrapperImpl<DocumentModel>(doc);
224 handler.handle(Action.CREATE, wrapDoc);
225 // create document with documentmodel
226 setCollectionSpaceCoreValues(ctx, doc, Action.CREATE);
227 doc = repoSession.createDocument(doc);
229 handler.complete(Action.CREATE, wrapDoc);
231 } catch (BadRequestException bre) {
233 } catch (Exception e) {
234 if (logger.isDebugEnabled()) {
235 logger.debug("Caught exception ", e);
237 throw new DocumentException(e);
239 if (repoSession != null) {
240 releaseRepositorySession(repoSession);
247 * get document from the Nuxeo repository
248 * @param ctx service context under which this method is invoked
250 * of the document to retrieve
252 * should be used by the caller to provide and transform the
254 * @throws DocumentException
257 public void get(ServiceContext ctx, String id, DocumentHandler handler)
258 throws DocumentNotFoundException, DocumentException {
260 if (handler == null) {
261 throw new IllegalArgumentException(
262 "RepositoryJavaClient.get: handler is missing");
264 RepositoryInstance repoSession = null;
267 handler.prepare(Action.GET);
268 repoSession = getRepositorySession();
269 DocumentRef docRef = NuxeoUtils.createPathRef(ctx, id);
270 DocumentModel doc = null;
272 doc = repoSession.getDocument(docRef);
273 } catch (ClientException ce) {
274 String msg = "could not find document with id=" + id;
275 logger.error(msg, ce);
276 throw new DocumentNotFoundException(msg, ce);
278 //set reposession to handle the document
279 ((DocumentModelHandler) handler).setRepositorySession(repoSession);
280 DocumentWrapper<DocumentModel> wrapDoc = new DocumentWrapperImpl<DocumentModel>(doc);
281 handler.handle(Action.GET, wrapDoc);
282 handler.complete(Action.GET, wrapDoc);
283 } catch (IllegalArgumentException iae) {
285 } catch (DocumentException de) {
287 } catch (Exception e) {
288 if (logger.isDebugEnabled()) {
289 logger.debug("Caught exception ", e);
291 throw new DocumentException(e);
293 if (repoSession != null) {
294 releaseRepositorySession(repoSession);
300 * get document from the Nuxeo repository, using the docFilter params.
301 * @param ctx service context under which this method is invoked
303 * should be used by the caller to provide and transform the
304 * document. Handler must have a docFilter set to return a single item.
305 * @throws DocumentException
308 public void get(ServiceContext ctx, DocumentHandler handler)
309 throws DocumentNotFoundException, DocumentException {
310 QueryContext queryContext = new QueryContext(ctx, handler);
311 RepositoryInstance repoSession = null;
314 handler.prepare(Action.GET);
315 repoSession = getRepositorySession();
317 DocumentModelList docList = null;
318 // force limit to 1, and ignore totalSize
319 String query = buildNXQLQuery(queryContext);
320 docList = repoSession.query(query, null, 1, 0, false);
321 if (docList.size() != 1) {
322 throw new DocumentNotFoundException("No document found matching filter params.");
324 DocumentModel doc = docList.get(0);
326 if (logger.isDebugEnabled()) {
327 logger.debug("Executed NXQL query: " + query);
330 //set reposession to handle the document
331 ((DocumentModelHandler) handler).setRepositorySession(repoSession);
332 DocumentWrapper<DocumentModel> wrapDoc = new DocumentWrapperImpl<DocumentModel>(doc);
333 handler.handle(Action.GET, wrapDoc);
334 handler.complete(Action.GET, wrapDoc);
335 } catch (IllegalArgumentException iae) {
337 } catch (DocumentException de) {
339 } catch (Exception e) {
340 if (logger.isDebugEnabled()) {
341 logger.debug("Caught exception ", e);
343 throw new DocumentException(e);
345 if (repoSession != null) {
346 releaseRepositorySession(repoSession);
352 * get wrapped documentModel from the Nuxeo repository
353 * @param ctx service context under which this method is invoked
355 * of the document to retrieve
356 * @throws DocumentException
359 public DocumentWrapper<DocumentModel> getDoc(
360 ServiceContext ctx, String id)
361 throws DocumentNotFoundException, DocumentException {
362 RepositoryInstance repoSession = null;
363 DocumentWrapper<DocumentModel> wrapDoc = null;
366 repoSession = getRepositorySession();
367 DocumentRef docRef = NuxeoUtils.createPathRef(ctx, id);
368 DocumentModel doc = null;
370 doc = repoSession.getDocument(docRef);
371 } catch (ClientException ce) {
372 String msg = "could not find document with id=" + id;
373 logger.error(msg, ce);
374 throw new DocumentNotFoundException(msg, ce);
376 wrapDoc = new DocumentWrapperImpl<DocumentModel>(doc);
377 } catch (IllegalArgumentException iae) {
379 } catch (DocumentException de) {
381 } catch (Exception e) {
382 if (logger.isDebugEnabled()) {
383 logger.debug("Caught exception ", e);
385 throw new DocumentException(e);
387 if (repoSession != null) {
388 releaseRepositorySession(repoSession);
395 * find wrapped documentModel from the Nuxeo repository
396 * @param ctx service context under which this method is invoked
397 * @param where NXQL where clause to get the document
398 * @throws DocumentException
401 public DocumentWrapper<DocumentModel> findDoc(
402 ServiceContext ctx, String whereClause)
403 throws DocumentNotFoundException, DocumentException {
404 RepositoryInstance repoSession = null;
405 DocumentWrapper<DocumentModel> wrapDoc = null;
408 QueryContext queryContext = new QueryContext(ctx, whereClause);
409 repoSession = getRepositorySession();
410 DocumentModelList docList = null;
411 // force limit to 1, and ignore totalSize
412 String query = buildNXQLQuery(queryContext);
413 docList = repoSession.query(query,
418 if (docList.size() != 1) {
419 if (logger.isDebugEnabled()) {
420 logger.debug("findDoc: Query found: " + docList.size() + " items.");
421 logger.debug(" Query: " + query);
423 throw new DocumentNotFoundException("No document found matching filter params.");
425 DocumentModel doc = docList.get(0);
426 wrapDoc = new DocumentWrapperImpl<DocumentModel>(doc);
427 } catch (IllegalArgumentException iae) {
429 } catch (DocumentException de) {
431 } catch (Exception e) {
432 if (logger.isDebugEnabled()) {
433 logger.debug("Caught exception ", e);
435 throw new DocumentException(e);
437 if (repoSession != null) {
438 releaseRepositorySession(repoSession);
445 * find doc and return CSID from the Nuxeo repository
446 * @param ctx service context under which this method is invoked
447 * @param where NXQL where clause to get the document
448 * @throws DocumentException
451 public String findDocCSID(
452 ServiceContext ctx, String whereClause)
453 throws DocumentNotFoundException, DocumentException {
456 DocumentWrapper<DocumentModel> wrapDoc = findDoc(ctx, whereClause);
457 DocumentModel docModel = wrapDoc.getWrappedObject();
458 csid = NuxeoUtils.extractId(docModel.getPathAsString());
459 } catch (DocumentNotFoundException dnfe) {
461 } catch (IllegalArgumentException iae) {
463 } catch (DocumentException de) {
465 } catch (Exception e) {
466 if (logger.isDebugEnabled()) {
467 logger.debug("Caught exception ", e);
469 throw new DocumentException(e);
475 * Find a list of documentModels from the Nuxeo repository
476 * @param docTypes a list of DocType names to match
477 * @param where the clause to qualify on
478 * @param domain the domain for the associated services
482 public DocumentWrapper<DocumentModelList> findDocs(
484 List<String> docTypes,
486 int pageSize, int pageNum, boolean computeTotal)
487 throws DocumentNotFoundException, DocumentException {
488 RepositoryInstance repoSession = null;
489 DocumentWrapper<DocumentModelList> wrapDoc = null;
492 if (docTypes == null || docTypes.size() < 1) {
493 throw new DocumentNotFoundException(
494 "findDocs must specify at least one DocumentType.");
496 repoSession = getRepositorySession();
497 DocumentModelList docList = null;
498 // force limit to 1, and ignore totalSize
499 QueryContext queryContext = new QueryContext(ctx, whereClause);
500 String query = buildNXQLQuery(docTypes, queryContext);
501 docList = repoSession.query(query, null, pageSize, pageNum, computeTotal);
502 wrapDoc = new DocumentWrapperImpl<DocumentModelList>(docList);
503 } catch (IllegalArgumentException iae) {
505 } catch (Exception e) {
506 if (logger.isDebugEnabled()) {
507 logger.debug("Caught exception ", e);
509 throw new DocumentException(e);
511 if (repoSession != null) {
512 releaseRepositorySession(repoSession);
519 * @see org.collectionspace.services.common.storage.StorageClient#get(org.collectionspace.services.common.context.ServiceContext, java.util.List, org.collectionspace.services.common.document.DocumentHandler)
522 public void get(ServiceContext ctx, List<String> csidList, DocumentHandler handler)
523 throws DocumentNotFoundException, DocumentException {
524 if (handler == null) {
525 throw new IllegalArgumentException(
526 "RepositoryJavaClient.getAll: handler is missing");
529 RepositoryInstance repoSession = null;
532 handler.prepare(Action.GET_ALL);
533 repoSession = getRepositorySession();
534 DocumentModelList docModelList = new DocumentModelListImpl();
535 //FIXME: Should be using NuxeoUtils.createPathRef for security reasons
536 for (String csid : csidList) {
537 DocumentRef docRef = NuxeoUtils.createPathRef(ctx, csid);
538 DocumentModel docModel = repoSession.getDocument(docRef);
539 docModelList.add(docModel);
542 //set reposession to handle the document
543 ((DocumentModelHandler) handler).setRepositorySession(repoSession);
544 DocumentWrapper<DocumentModelList> wrapDoc = new DocumentWrapperImpl<DocumentModelList>(docModelList);
545 handler.handle(Action.GET_ALL, wrapDoc);
546 handler.complete(Action.GET_ALL, wrapDoc);
547 } catch (DocumentException de) {
549 } catch (Exception e) {
550 if (logger.isDebugEnabled()) {
551 logger.debug("Caught exception ", e);
553 throw new DocumentException(e);
555 if (repoSession != null) {
556 releaseRepositorySession(repoSession);
562 * getAll get all documents for an entity entity service from the Nuxeo
565 * @param ctx service context under which this method is invoked
567 * should be used by the caller to provide and transform the
569 * @throws DocumentException
572 public void getAll(ServiceContext ctx, DocumentHandler handler)
573 throws DocumentNotFoundException, DocumentException {
574 if (handler == null) {
575 throw new IllegalArgumentException(
576 "RepositoryJavaClient.getAll: handler is missing");
578 String nuxeoWspaceId = ctx.getRepositoryWorkspaceId();
579 if (nuxeoWspaceId == null) {
580 throw new DocumentNotFoundException(
581 "Unable to find workspace for service "
582 + ctx.getServiceName()
583 + " check if the workspace exists in the Nuxeo repository");
585 RepositoryInstance repoSession = null;
588 handler.prepare(Action.GET_ALL);
589 repoSession = getRepositorySession();
590 DocumentRef wsDocRef = new IdRef(nuxeoWspaceId);
591 DocumentModelList docList = repoSession.getChildren(wsDocRef);
592 //set reposession to handle the document
593 ((DocumentModelHandler) handler).setRepositorySession(repoSession);
594 DocumentWrapper<DocumentModelList> wrapDoc = new DocumentWrapperImpl<DocumentModelList>(docList);
595 handler.handle(Action.GET_ALL, wrapDoc);
596 handler.complete(Action.GET_ALL, wrapDoc);
597 } catch (DocumentException de) {
599 } catch (Exception e) {
600 if (logger.isDebugEnabled()) {
601 logger.debug("Caught exception ", e);
603 throw new DocumentException(e);
605 if (repoSession != null) {
606 releaseRepositorySession(repoSession);
612 * getFiltered get all documents for an entity service from the Document repository,
613 * given filter parameters specified by the handler.
614 * @param ctx service context under which this method is invoked
615 * @param handler should be used by the caller to provide and transform the document
616 * @throws DocumentNotFoundException if workspace not found
617 * @throws DocumentException
620 public void getFiltered(ServiceContext ctx, DocumentHandler handler)
621 throws DocumentNotFoundException, DocumentException {
622 QueryContext queryContext = new QueryContext(ctx, handler);
624 RepositoryInstance repoSession = null;
626 handler.prepare(Action.GET_ALL);
627 repoSession = getRepositorySession();
628 DocumentModelList docList = null;
629 String query = buildNXQLQuery(queryContext);
631 if (logger.isDebugEnabled()) {
632 logger.debug("Executing NXQL query: " + query.toString());
635 // If we have limit and/or offset, then pass true to get totalSize
636 // in returned DocumentModelList.
637 if ((queryContext.docFilter.getOffset() > 0) || (queryContext.docFilter.getPageSize() > 0)) {
638 docList = repoSession.query(query, null,
639 queryContext.docFilter.getPageSize(), queryContext.docFilter.getOffset(), true);
641 docList = repoSession.query(query);
644 //set repoSession to handle the document
645 ((DocumentModelHandler) handler).setRepositorySession(repoSession);
646 DocumentWrapper<DocumentModelList> wrapDoc = new DocumentWrapperImpl<DocumentModelList>(docList);
647 handler.handle(Action.GET_ALL, wrapDoc);
648 handler.complete(Action.GET_ALL, wrapDoc);
649 } catch (DocumentException de) {
651 } catch (Exception e) {
652 if (logger.isDebugEnabled()) {
653 logger.debug("Caught exception ", e);
655 throw new DocumentException(e);
657 if (repoSession != null) {
658 releaseRepositorySession(repoSession);
664 * update given document in the Nuxeo repository
666 * @param ctx service context under which this method is invoked
670 * should be used by the caller to provide and transform the
672 * @throws DocumentException
675 public void update(ServiceContext ctx, String id, DocumentHandler handler)
676 throws BadRequestException, DocumentNotFoundException,
678 if (handler == null) {
679 throw new IllegalArgumentException(
680 "RepositoryJavaClient.update: handler is missing");
682 RepositoryInstance repoSession = null;
684 handler.prepare(Action.UPDATE);
685 repoSession = getRepositorySession();
686 DocumentRef docRef = NuxeoUtils.createPathRef(ctx, id);
687 DocumentModel doc = null;
689 doc = repoSession.getDocument(docRef);
690 } catch (ClientException ce) {
691 String msg = "Could not find document to update with id=" + id;
692 logger.error(msg, ce);
693 throw new DocumentNotFoundException(msg, ce);
695 //set reposession to handle the document
696 ((DocumentModelHandler) handler).setRepositorySession(repoSession);
697 DocumentWrapper<DocumentModel> wrapDoc = new DocumentWrapperImpl<DocumentModel>(doc);
698 handler.handle(Action.UPDATE, wrapDoc);
699 setCollectionSpaceCoreValues(ctx, doc, Action.CREATE);
700 repoSession.saveDocument(doc);
702 handler.complete(Action.UPDATE, wrapDoc);
703 } catch (BadRequestException bre) {
705 } catch (DocumentException de) {
707 } catch (Exception e) {
708 if (logger.isDebugEnabled()) {
709 logger.debug("Caught exception ", e);
711 throw new DocumentException(e);
713 if (repoSession != null) {
714 releaseRepositorySession(repoSession);
720 * delete a document from the Nuxeo repository
721 * @param ctx service context under which this method is invoked
724 * @throws DocumentException
727 public void delete(ServiceContext ctx, String id) throws DocumentNotFoundException,
730 if (logger.isDebugEnabled()) {
731 logger.debug("deleting document with id=" + id);
733 RepositoryInstance repoSession = null;
735 repoSession = getRepositorySession();
736 DocumentRef docRef = NuxeoUtils.createPathRef(ctx, id);
738 repoSession.removeDocument(docRef);
739 } catch (ClientException ce) {
740 String msg = "could not find document to delete with id=" + id;
741 logger.error(msg, ce);
742 throw new DocumentNotFoundException(msg, ce);
745 } catch (DocumentException de) {
747 } catch (Exception e) {
748 if (logger.isDebugEnabled()) {
749 logger.debug("Caught exception ", e);
751 throw new DocumentException(e);
753 if (repoSession != null) {
754 releaseRepositorySession(repoSession);
760 * @see org.collectionspace.services.common.storage.StorageClient#delete(org.collectionspace.services.common.context.ServiceContext, java.lang.String, org.collectionspace.services.common.document.DocumentHandler)
763 public void delete(ServiceContext ctx, String id, DocumentHandler handler)
764 throws DocumentNotFoundException, DocumentException {
765 throw new UnsupportedOperationException();
769 public Hashtable<String, String> retrieveWorkspaceIds(String domainName) throws Exception {
770 return NuxeoConnector.getInstance().retrieveWorkspaceIds(domainName);
774 public String createDomain(String domainName) throws Exception {
775 RepositoryInstance repoSession = null;
776 String domainId = null;
778 repoSession = getRepositorySession();
779 DocumentRef parentDocRef = new PathRef("/");
780 DocumentModel parentDoc = repoSession.getDocument(parentDocRef);
781 DocumentModel doc = repoSession.createDocumentModel(parentDoc.getPathAsString(),
782 domainName, "Domain");
783 doc.setPropertyValue("dc:title", domainName);
784 doc.setPropertyValue("dc:description", "A CollectionSpace domain "
786 doc = repoSession.createDocument(doc);
787 domainId = doc.getId();
789 if (logger.isDebugEnabled()) {
790 logger.debug("created tenant domain name=" + domainName
791 + " id=" + domainId);
793 } catch (Exception e) {
794 if (logger.isDebugEnabled()) {
795 logger.debug("createTenantSpace caught exception ", e);
799 if (repoSession != null) {
800 releaseRepositorySession(repoSession);
807 public String getDomainId(String domainName) throws Exception {
808 String domainId = null;
809 RepositoryInstance repoSession = null;
811 repoSession = getRepositorySession();
812 DocumentRef docRef = new PathRef(
814 DocumentModel domain = repoSession.getDocument(docRef);
815 domainId = domain.getId();
816 } catch (Exception e) {
817 if (logger.isDebugEnabled()) {
818 logger.debug("Caught exception ", e);
820 //there is no way to identify if document does not exist due to
821 //lack of typed exception for getDocument method
824 if (repoSession != null) {
825 releaseRepositorySession(repoSession);
832 * @see org.collectionspace.services.common.repository.RepositoryClient#createWorkspace(java.lang.String, java.lang.String)
835 public String createWorkspace(String domainName, String workspaceName) throws Exception {
836 RepositoryInstance repoSession = null;
837 String workspaceId = null;
839 repoSession = getRepositorySession();
840 DocumentRef parentDocRef = new PathRef(
842 + "/" + "workspaces");
843 DocumentModel parentDoc = repoSession.getDocument(parentDocRef);
844 DocumentModel doc = repoSession.createDocumentModel(parentDoc.getPathAsString(),
845 workspaceName, "Workspace");
846 doc.setPropertyValue("dc:title", workspaceName);
847 doc.setPropertyValue("dc:description", "A CollectionSpace workspace for "
849 doc = repoSession.createDocument(doc);
850 workspaceId = doc.getId();
852 if (logger.isDebugEnabled()) {
853 logger.debug("created workspace name=" + workspaceName
854 + " id=" + workspaceId);
856 } catch (Exception e) {
857 if (logger.isDebugEnabled()) {
858 logger.debug("createWorkspace caught exception ", e);
862 if (repoSession != null) {
863 releaseRepositorySession(repoSession);
870 * @see org.collectionspace.services.common.repository.RepositoryClient#getWorkspaceId(java.lang.String, java.lang.String)
873 public String getWorkspaceId(String tenantDomain, String workspaceName) throws Exception {
874 String workspaceId = null;
875 RepositoryInstance repoSession = null;
877 repoSession = getRepositorySession();
878 DocumentRef docRef = new PathRef(
881 + "/" + workspaceName);
882 DocumentModel workspace = repoSession.getDocument(docRef);
883 workspaceId = workspace.getId();
884 } catch (DocumentException de) {
886 } catch (Exception e) {
887 if (logger.isDebugEnabled()) {
888 logger.debug("Caught exception ", e);
890 throw new DocumentException(e);
892 if (repoSession != null) {
893 releaseRepositorySession(repoSession);
902 * @param query the query
903 * @param where the where
904 * @param domain the domain
906 private final void appendNXQLWhere(StringBuilder query, QueryContext queryContext) {
908 // Restrict search to a specific Nuxeo domain
909 // TODO This is a slow method for tenant-filter
910 // We should make this a property that is indexed.
912 query.append(" WHERE ecm:path STARTSWITH '/" + queryContext.domain + "'");
915 // Restrict search to the current tenant ID. Is the domain path filter (above) still needed?
917 query.append(IQueryManager.SEARCH_QUALIFIER_AND + DocumentModelHandler.COLLECTIONSPACE_CORE_SCHEMA + ":"
918 + DocumentModelHandler.COLLECTIONSPACE_CORE_TENANTID
919 + " = " + queryContext.tenantId);
921 // Finally, append the incoming where clause
923 String whereClause = queryContext.whereClause;
924 if (whereClause != null && whereClause.length() > 0) {
925 // Due to an apparent bug/issue in how Nuxeo translates the NXQL query string
926 // into SQL, we need to parenthesize our 'where' clause
927 query.append(IQueryManager.SEARCH_QUALIFIER_AND + "(" + whereClause + ")");
930 // Please lookup this use in Nuxeo support and document here
932 query.append(IQueryManager.SEARCH_QUALIFIER_AND + "ecm:isProxy = 0");
936 * Builds the nxql query.
938 * @param docType the doc type
939 * @param where the where
940 * @param domain the domain
941 * @param tenantId the tenant id
944 private final String buildNXQLQuery(QueryContext queryContext) {
945 StringBuilder query = new StringBuilder("SELECT * FROM ");
946 query.append(queryContext.docType);
947 appendNXQLWhere(query, queryContext);
948 return query.toString();
952 * Builds the nxql query.
954 * @param docTypes the doc types
955 * @param where the where
956 * @param domain the domain
959 private final String buildNXQLQuery(List<String> docTypes, QueryContext queryContext) {
960 StringBuilder query = new StringBuilder("SELECT * FROM ");
961 boolean fFirst = true;
962 for (String docType : docTypes) {
968 query.append(docType);
970 appendNXQLWhere(query, queryContext);
971 return query.toString();
975 * Gets the repository session.
977 * @return the repository session
978 * @throws Exception the exception
980 private RepositoryInstance getRepositorySession() throws Exception {
981 // FIXME: is it possible to reuse repository session?
982 // Authentication failures happen while trying to reuse the session
983 NuxeoClient client = NuxeoConnector.getInstance().getClient();
984 RepositoryInstance repoSession = client.openRepository();
985 if (logger.isDebugEnabled()) {
986 logger.debug("getRepository() repository root: " + repoSession.getRootDocument());
992 * Release repository session.
994 * @param repoSession the repo session
996 private void releaseRepositorySession(RepositoryInstance repoSession) {
998 NuxeoClient client = NuxeoConnector.getInstance().getClient();
1000 client.releaseRepository(repoSession);
1001 } catch (Exception e) {
1002 logger.error("Could not close the repository session", e);
1003 // no need to throw this service specific exception