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 * $LastChangedRevision$
26 package org.collectionspace.services.collectionobject;
28 import java.util.ArrayList;
29 import java.util.List;
31 import javax.ws.rs.Consumes;
32 import javax.ws.rs.DELETE;
33 import javax.ws.rs.GET;
34 import javax.ws.rs.POST;
35 import javax.ws.rs.PUT;
36 import javax.ws.rs.Path;
37 import javax.ws.rs.PathParam;
38 import javax.ws.rs.Produces;
39 import javax.ws.rs.QueryParam;
40 import javax.ws.rs.WebApplicationException;
41 import javax.ws.rs.core.Context;
42 import javax.ws.rs.core.Response;
43 import javax.ws.rs.core.UriBuilder;
44 import javax.ws.rs.core.UriInfo;
45 import javax.ws.rs.core.MultivaluedMap;
47 import org.collectionspace.services.common.imaging.nuxeo.NuxeoImageUtils;
48 import org.collectionspace.services.common.AbstractMultiPartCollectionSpaceResourceImpl;
49 import org.collectionspace.services.common.authorityref.AuthorityRefList;
50 import org.collectionspace.services.common.context.ServiceContextFactory;
51 //import org.collectionspace.services.common.context.MultipartServiceContext;
52 import org.collectionspace.services.common.context.MultipartServiceContextFactory;
53 import org.collectionspace.services.common.context.MultipartServiceContextImpl;
54 import org.collectionspace.services.common.context.ServiceBindingUtils;
55 import org.collectionspace.services.common.context.ServiceContext;
56 import org.collectionspace.services.common.document.BadRequestException;
57 import org.collectionspace.services.common.document.DocumentFilter;
58 import org.collectionspace.services.common.document.DocumentHandler;
59 import org.collectionspace.services.common.document.DocumentNotFoundException;
60 import org.collectionspace.services.common.document.DocumentWrapper;
61 import org.collectionspace.services.common.query.IQueryManager;
62 import org.collectionspace.services.common.query.QueryManager;
63 import org.collectionspace.services.common.security.UnauthorizedException;
64 import org.collectionspace.services.common.vocabulary.RefNameServiceUtils;
65 import org.collectionspace.services.intake.IntakeResource;
66 import org.collectionspace.services.intake.IntakesCommonList;
67 //import org.collectionspace.services.nuxeo.client.java.RemoteDocumentModelHandlerImpl;
68 import org.collectionspace.services.nuxeo.client.java.DocumentModelHandler;
69 import org.collectionspace.services.relation.NewRelationResource;
70 import org.collectionspace.services.relation.RelationsCommonList;
71 import org.collectionspace.services.relation.RelationshipType;
72 import org.collectionspace.services.common.profile.Profiler;
74 import org.jboss.resteasy.plugins.providers.multipart.MultipartInput;
75 import org.jboss.resteasy.plugins.providers.multipart.MultipartOutput;
76 import org.jboss.resteasy.util.HttpResponseCodes;
78 import org.nuxeo.ecm.core.api.DocumentModel;
80 import org.slf4j.Logger;
81 import org.slf4j.LoggerFactory;
85 * The Class CollectionObjectResource.
87 @Path("/collectionobjects")
88 @Consumes("multipart/mixed")
89 @Produces("multipart/mixed")
90 public class CollectionObjectResource
91 extends AbstractMultiPartCollectionSpaceResourceImpl {
93 /** The Constant serviceName. */
94 static final public String serviceName = "collectionobjects";
97 final Logger logger = LoggerFactory.getLogger(CollectionObjectResource.class);
100 * @see org.collectionspace.services.common.AbstractCollectionSpaceResourceImpl#getVersionString()
103 public String getVersionString() {
104 /** The last change revision. */
105 final String lastChangeRevision = "$LastChangedRevision$";
106 return lastChangeRevision;
110 * @see org.collectionspace.services.common.AbstractCollectionSpaceResourceImpl#getServiceName()
113 public String getServiceName() {
118 * @see org.collectionspace.services.common.CollectionSpaceResource#getCommonPartClass()
121 public Class<CollectionobjectsCommon> getCommonPartClass() {
122 return CollectionobjectsCommon.class;
126 * @see org.collectionspace.services.common.AbstractCollectionSpaceResourceImpl#createDocumentHandler(org.collectionspace.services.common.context.ServiceContext)
129 // public DocumentHandler createDocumentHandler(ServiceContext<MultipartInput, MultipartOutput> ctx) throws Exception {
130 // DocumentHandler docHandler = ctx.getDocumentHandler();
131 // if (ctx.getInput() != null) {
132 // Object obj = ((MultipartServiceContext) ctx).getInputPart(ctx.getCommonPartLabel(),
133 // CollectionobjectsCommon.class);
134 // if (obj != null) {
135 // docHandler.setCommonPart((CollectionobjectsCommon) obj);
138 // return docHandler;
142 * Creates the collection object.
144 * @param input the input
146 * @return the response
149 public Response createCollectionObject(MultipartInput input) {
151 ServiceContext<MultipartInput, MultipartOutput> ctx = createServiceContext(input); //
152 DocumentHandler handler = createDocumentHandler(ctx);
153 String csid = getRepositoryClient(ctx).create(ctx, handler);
154 UriBuilder path = UriBuilder.fromResource(CollectionObjectResource.class);
155 path.path("" + csid);
156 Response response = Response.created(path.build()).build();
158 } catch (BadRequestException bre) {
159 Response response = Response.status(
160 Response.Status.BAD_REQUEST).entity("Create failed reason " + bre.getErrorReason()).type("text/plain").build();
161 throw new WebApplicationException(response);
162 } catch (UnauthorizedException ue) {
163 Response response = Response.status(
164 Response.Status.UNAUTHORIZED).entity("Create failed reason " + ue.getErrorReason()).type("text/plain").build();
165 throw new WebApplicationException(response);
166 } catch (Exception e) {
167 if (logger.isDebugEnabled()) {
168 logger.debug("Caught exception in createCollectionObject", e);
170 Response response = Response.status(
171 Response.Status.INTERNAL_SERVER_ERROR).entity("Create failed").type("text/plain").build();
172 throw new WebApplicationException(response);
177 * Gets the collection object.
179 * @param csid the csid
181 * @return the collection object
185 public MultipartOutput getCollectionObject(
186 @PathParam("csid") String csid) {
187 if (logger.isDebugEnabled()) {
188 logger.debug("getCollectionObject with csid=" + csid);
190 if (csid == null || "".equals(csid)) {
191 logger.error("getCollectionObject: missing csid!");
192 Response response = Response.status(Response.Status.BAD_REQUEST).entity(
193 "get failed on CollectionObject csid=" + csid).type(
194 "text/plain").build();
195 throw new WebApplicationException(response);
197 MultipartOutput result = null;
199 ServiceContext<MultipartInput, MultipartOutput> ctx = createServiceContext();
200 DocumentHandler handler = createDocumentHandler(ctx);
201 getRepositoryClient(ctx).get(ctx, csid, handler);
202 result = (MultipartOutput) ctx.getOutput();
203 } catch (UnauthorizedException ue) {
204 Response response = Response.status(
205 Response.Status.UNAUTHORIZED).entity("Get failed reason " + ue.getErrorReason()).type("text/plain").build();
206 throw new WebApplicationException(response);
207 } catch (DocumentNotFoundException dnfe) {
208 if (logger.isDebugEnabled()) {
209 logger.debug("getCollectionObject", dnfe);
211 Response response = Response.status(Response.Status.NOT_FOUND).entity(
212 "Get failed on CollectionObject csid=" + csid).type(
213 "text/plain").build();
214 throw new WebApplicationException(response);
215 } catch (Exception e) {
216 if (logger.isDebugEnabled()) {
217 logger.debug("getCollectionObject", e);
219 Response response = Response.status(
220 Response.Status.INTERNAL_SERVER_ERROR).entity("Get failed").type("text/plain").build();
221 throw new WebApplicationException(response);
224 if (result == null) {
225 Response response = Response.status(Response.Status.NOT_FOUND).entity(
226 "Get failed, the requested CollectionObject CSID:" + csid + ": was not found.").type(
227 "text/plain").build();
228 throw new WebApplicationException(response);
234 * Gets the collection object list.
237 * @param keywords the keywords
239 * @return the collection object list
242 @Produces("application/xml")
243 public CollectionobjectsCommonList getCollectionObjectList(@Context UriInfo ui,
244 @QueryParam(IQueryManager.SEARCH_TYPE_KEYWORDS_KW) String keywords) {
245 Profiler profiler = new Profiler("getCollectionObjectList():", 1);
247 CollectionobjectsCommonList result = null;
248 MultivaluedMap<String, String> queryParams = ui.getQueryParameters();
249 if (keywords != null) {
250 result = searchCollectionObjects(queryParams, keywords);
252 result = getCollectionObjectList(queryParams);
259 * Gets the collection object list.
261 private CollectionobjectsCommonList getCollectionObjectList(MultivaluedMap<String, String> queryParams) {
262 CollectionobjectsCommonList collectionObjectList;
263 Profiler profiler = new Profiler(this, 1);
267 ServiceContext<MultipartInput, MultipartOutput> ctx = createServiceContext(queryParams);
268 DocumentHandler handler = createDocumentHandler(ctx);
269 getRepositoryClient(ctx).getFiltered(ctx, handler);
270 collectionObjectList = (CollectionobjectsCommonList) handler.getCommonPartList();
271 } catch (UnauthorizedException ue) {
272 Response response = Response.status(
273 Response.Status.UNAUTHORIZED).entity("Index failed reason " + ue.getErrorReason()).type("text/plain").build();
274 throw new WebApplicationException(response);
275 } catch (Exception e) {
276 if (logger.isDebugEnabled()) {
277 logger.debug("Caught exception in getCollectionObjectList", e);
279 Response response = Response.status(
280 Response.Status.INTERNAL_SERVER_ERROR).entity("Index failed").type("text/plain").build();
281 throw new WebApplicationException(response);
285 return collectionObjectList;
289 * Update collection object.
291 * @param csid the csid
292 * @param theUpdate the the update
294 * @return the multipart output
298 public MultipartOutput updateCollectionObject(
299 @PathParam("csid") String csid,
300 MultipartInput theUpdate) {
301 if (logger.isDebugEnabled()) {
302 logger.debug("updateCollectionObject with csid=" + csid);
304 if (csid == null || "".equals(csid)) {
305 logger.error("updateCollectionObject: missing csid!");
306 Response response = Response.status(Response.Status.BAD_REQUEST).entity(
307 "update failed on CollectionObject csid=" + csid).type(
308 "text/plain").build();
309 throw new WebApplicationException(response);
311 MultipartOutput result = null;
313 ServiceContext<MultipartInput, MultipartOutput> ctx = createServiceContext(theUpdate);
314 DocumentHandler handler = createDocumentHandler(ctx);
315 getRepositoryClient(ctx).update(ctx, csid, handler);
316 result = (MultipartOutput) ctx.getOutput();
317 } catch (BadRequestException bre) {
318 Response response = Response.status(
319 Response.Status.BAD_REQUEST).entity("Update failed reason " + bre.getErrorReason()).type("text/plain").build();
320 throw new WebApplicationException(response);
321 } catch (UnauthorizedException ue) {
322 Response response = Response.status(
323 Response.Status.UNAUTHORIZED).entity("Update failed reason " + ue.getErrorReason()).type("text/plain").build();
324 throw new WebApplicationException(response);
325 } catch (DocumentNotFoundException dnfe) {
326 if (logger.isDebugEnabled()) {
327 logger.debug("caugth exception in updateCollectionObject", dnfe);
329 Response response = Response.status(Response.Status.NOT_FOUND).entity(
330 "Update failed on CollectionObject csid=" + csid).type(
331 "text/plain").build();
332 throw new WebApplicationException(response);
333 } catch (Exception e) {
334 Response response = Response.status(
335 Response.Status.INTERNAL_SERVER_ERROR).entity("Update failed").type("text/plain").build();
336 throw new WebApplicationException(response);
342 * Delete collection object.
344 * @param csid the csid
346 * @return the response
350 public Response deleteCollectionObject(@PathParam("csid") String csid) {
352 if (logger.isDebugEnabled()) {
353 logger.debug("deleteCollectionObject with csid=" + csid);
355 if (csid == null || "".equals(csid)) {
356 logger.error("deleteCollectionObject: missing csid!");
357 Response response = Response.status(Response.Status.BAD_REQUEST).entity(
358 "delete failed on CollectionObject csid=" + csid).type(
359 "text/plain").build();
360 throw new WebApplicationException(response);
363 ServiceContext<MultipartInput, MultipartOutput> ctx = createServiceContext();
364 getRepositoryClient(ctx).delete(ctx, csid);
365 return Response.status(HttpResponseCodes.SC_OK).build();
366 } catch (UnauthorizedException ue) {
367 Response response = Response.status(
368 Response.Status.UNAUTHORIZED).entity("Delete failed reason " + ue.getErrorReason()).type("text/plain").build();
369 throw new WebApplicationException(response);
370 } catch (DocumentNotFoundException dnfe) {
371 if (logger.isDebugEnabled()) {
372 logger.debug("caught exception in deleteCollectionObject", dnfe);
374 Response response = Response.status(Response.Status.NOT_FOUND).entity(
375 "Delete failed on CollectionObject csid=" + csid).type(
376 "text/plain").build();
377 throw new WebApplicationException(response);
378 } catch (Exception e) {
379 Response response = Response.status(
380 Response.Status.INTERNAL_SERVER_ERROR).entity("Delete failed").type("text/plain").build();
381 throw new WebApplicationException(response);
387 * Gets the intakes common list.
390 * @param csid the csid
392 * @return the intakes common list
395 @Path("{csid}/intakes")
396 @Produces("application/xml")
397 public IntakesCommonList getIntakesCommonList(@Context UriInfo ui,
398 @PathParam("csid") String csid) {
399 IntakesCommonList result = null;
400 MultivaluedMap<String, String> queryParams = ui.getQueryParameters();
404 // Find all the intake-related relation records.
406 String subjectCsid = csid;
407 String predicate = RelationshipType.COLLECTIONOBJECT_INTAKE.value();
408 String objectCsid = null;
409 NewRelationResource relationResource = new NewRelationResource();
410 RelationsCommonList relationsCommonList = relationResource.getRelationList(queryParams,
412 null, /*subjectType*/
415 null /*objectType*/);
418 // Create an array of Intake csid's
420 List<RelationsCommonList.RelationListItem> relationsListItems = relationsCommonList.getRelationListItem();
421 List<String> intakeCsidList = new ArrayList<String>();
422 for (RelationsCommonList.RelationListItem relationsListItem : relationsListItems) {
423 intakeCsidList.add(relationsListItem.getObjectCsid());
427 // Get a response list for the Intake records from the Intake resource
429 IntakeResource intakeResource = new IntakeResource();
430 result = intakeResource.getIntakeList(intakeCsidList);
431 } catch (Exception e) {
432 if (logger.isDebugEnabled()) {
433 logger.debug("Caught exception in getIntakeList", e);
435 Response response = Response.status(
436 Response.Status.INTERNAL_SERVER_ERROR).entity("Index failed").type("text/plain").build();
437 throw new WebApplicationException(response);
444 * Gets the authority refs.
446 * @param csid the csid
449 * @return the authority refs
452 @Path("{csid}/authorityrefs")
453 @Produces("application/xml")
454 public AuthorityRefList getAuthorityRefs(
455 @PathParam("csid") String csid,
456 @Context UriInfo ui) {
457 AuthorityRefList authRefList = null;
459 MultivaluedMap<String, String> queryParams = ui.getQueryParameters();
460 ServiceContext<MultipartInput, MultipartOutput> ctx = createServiceContext(queryParams);
461 DocumentWrapper<DocumentModel> docWrapper =
462 getRepositoryClient(ctx).getDoc(ctx, csid);
463 DocumentModelHandler<MultipartInput, MultipartOutput> docHandler =
464 (DocumentModelHandler<MultipartInput, MultipartOutput>)createDocumentHandler(ctx);
465 List<String> authRefFields =
466 ((MultipartServiceContextImpl)ctx).getCommonPartPropertyValues(
467 ServiceBindingUtils.AUTH_REF_PROP, ServiceBindingUtils.QUALIFIED_PROP_NAMES);
468 authRefList = docHandler.getAuthorityRefs(docWrapper, authRefFields);
469 } catch (UnauthorizedException ue) {
470 Response response = Response.status(
471 Response.Status.UNAUTHORIZED).entity("Index failed reason " + ue.getErrorReason()).type("text/plain").build();
472 throw new WebApplicationException(response);
473 } catch (Exception e) {
474 if (logger.isDebugEnabled()) {
475 logger.debug("Caught exception in getAuthorityRefs", e);
477 Response response = Response.status(
478 Response.Status.INTERNAL_SERVER_ERROR).entity("Index failed").type("text/plain").build();
479 throw new WebApplicationException(response);
487 * This is an intentionally empty method used for getting a rough time estimate
488 * of the overhead required for a client->server request/response cycle.
489 * @param ms - milliseconds to delay
491 * @return the response
494 @Path("/{ms}/roundtrip")
495 @Produces("application/xml")
496 public Response roundtrip(
497 @PathParam("ms") String ms) {
498 Response result = null;
500 Profiler profiler = new Profiler("roundtrip():", 1);
502 result = Response.status(HttpResponseCodes.SC_OK).build();
510 @Produces("application/xml")
511 public Response createPictureDocument() {
512 Response result = null;
514 if (logger.isDebugEnabled()) {
515 logger.debug("------------------------------------------------------------------------------");
516 logger.debug("Prototype to create a Picture document in Nuxeo");
517 logger.debug("------------------------------------------------------------------------------");
521 NuxeoImageUtils.createPicture();
522 result = Response.status(HttpResponseCodes.SC_OK).build();
528 * This method is deprecated. Use kwSearchCollectionObjects() method instead.
529 * Keywords search collection objects.
532 * @param keywords the keywords
534 * @return the collectionobjects common list
538 @Produces("application/xml")
539 public CollectionobjectsCommonList keywordsSearchCollectionObjects(@Context UriInfo ui,
540 @QueryParam(IQueryManager.SEARCH_TYPE_KEYWORDS) String keywords) {
541 MultivaluedMap<String, String> queryParams = ui.getQueryParameters();
542 return searchCollectionObjects(queryParams, keywords);
546 * Search collection objects.
548 * @param keywords the keywords
550 * @return the collectionobjects common list
552 private CollectionobjectsCommonList searchCollectionObjects(
553 MultivaluedMap<String, String> queryParams,
555 CollectionobjectsCommonList collectionObjectList;
557 Profiler profiler = new Profiler("searchCollectionObjects():", 1);
559 ServiceContext<MultipartInput, MultipartOutput> ctx = createServiceContext(queryParams);
560 DocumentHandler handler = createDocumentHandler(ctx);
562 // perform a keyword search
563 if (keywords != null && !keywords.isEmpty()) {
564 String whereClause = QueryManager.createWhereClauseFromKeywords(keywords);
565 DocumentFilter documentFilter = handler.getDocumentFilter();
566 documentFilter.setWhereClause(whereClause);
567 if (logger.isDebugEnabled()) {
568 logger.debug("The WHERE clause is: " + documentFilter.getWhereClause());
572 getRepositoryClient(ctx).getFiltered(ctx, handler);
573 collectionObjectList = (CollectionobjectsCommonList) handler.getCommonPartList();
574 } catch (UnauthorizedException ue) {
575 Response response = Response.status(
576 Response.Status.UNAUTHORIZED).entity("Index failed reason " + ue.getErrorReason()).type("text/plain").build();
577 throw new WebApplicationException(response);
578 } catch (Exception e) {
579 if (logger.isDebugEnabled()) {
580 logger.debug("Caught exception in getCollectionObjectList", e);
582 Response response = Response.status(
583 Response.Status.INTERNAL_SERVER_ERROR).entity("Index failed").type("text/plain").build();
584 throw new WebApplicationException(response);
586 return collectionObjectList;