Name on share, share document (not file)

This commit is contained in:
jendib 2013-08-14 20:51:08 +02:00
parent 4cb5b7fdbb
commit 200d7a0001
14 changed files with 430 additions and 359 deletions

View File

@ -40,6 +40,19 @@ public class DocumentDao {
return document.getId(); return document.getId();
} }
/**
* Returns an active document.
*
* @param id Document ID
* @return Document
*/
public Document getDocument(String id) {
EntityManager em = ThreadLocalContext.get().getEntityManager();
Query q = em.createQuery("select d from Document d where d.id = :id and d.deleteDate is null");
q.setParameter("id", id);
return (Document) q.getSingleResult();
}
/** /**
* Returns an active document. * Returns an active document.
* *
@ -74,7 +87,12 @@ public class DocumentDao {
// Delete linked data // Delete linked data
q = em.createQuery("update File f set f.deleteDate = :dateNow where f.documentId = :documentId and f.deleteDate is null"); q = em.createQuery("update File f set f.deleteDate = :dateNow where f.documentId = :documentId and f.deleteDate is null");
q.setParameter("documentId", documentDb.getId()); q.setParameter("documentId", id);
q.setParameter("dateNow", dateNow);
q.executeUpdate();
q = em.createQuery("update Share s set s.deleteDate = :dateNow where s.documentId = :documentId and s.deleteDate is null");
q.setParameter("documentId", id);
q.setParameter("dateNow", dateNow); q.setParameter("dateNow", dateNow);
q.executeUpdate(); q.executeUpdate();
} }

View File

@ -64,12 +64,6 @@ public class FileDao {
// Delete the file // Delete the file
Date dateNow = new Date(); Date dateNow = new Date();
fileDb.setDeleteDate(dateNow); fileDb.setDeleteDate(dateNow);
// Delete linked data
q = em.createQuery("update FileShare fs set fs.deleteDate = :dateNow where fs.fileId = :fileId and fs.deleteDate is null");
q.setParameter("fileId", id);
q.setParameter("dateNow", dateNow);
q.executeUpdate();
} }
/** /**

View File

@ -1,102 +0,0 @@
package com.sismics.docs.core.dao.jpa;
import java.util.Date;
import java.util.List;
import java.util.UUID;
import javax.persistence.EntityManager;
import javax.persistence.NoResultException;
import javax.persistence.Query;
import com.sismics.docs.core.model.jpa.FileShare;
import com.sismics.util.context.ThreadLocalContext;
/**
* File share DAO.
*
* @author bgamard
*/
public class FileShareDao {
/**
* Creates a new file share.
*
* @param fileShare File share
* @return New ID
* @throws Exception
*/
public String create(FileShare fileShare) {
// Create the UUID
fileShare.setId(UUID.randomUUID().toString());
// Create the file
EntityManager em = ThreadLocalContext.get().getEntityManager();
fileShare.setCreateDate(new Date());
em.persist(fileShare);
return fileShare.getId();
}
/**
* Returns an active file share.
*
* @param id File ID
* @return Document
*/
public FileShare getFileShare(String id) {
EntityManager em = ThreadLocalContext.get().getEntityManager();
Query q = em.createQuery("select fs from FileShare fs where fs.id = :id and fs.deleteDate is null");
q.setParameter("id", id);
try {
return (FileShare) q.getSingleResult();
} catch (NoResultException e) {
return null;
}
}
/**
* Deletes a file share.
*
* @param id File ID
*/
public void delete(String id) {
EntityManager em = ThreadLocalContext.get().getEntityManager();
// Get the document
Query q = em.createQuery("select fs from FileShare fs where fs.id = :id and fs.deleteDate is null");
q.setParameter("id", id);
FileShare fileShareDb = (FileShare) q.getSingleResult();
// Delete the document
Date dateNow = new Date();
fileShareDb.setDeleteDate(dateNow);
}
/**
* Gets a file share by its ID.
*
* @param id Document ID
* @return Document
*/
public FileShare getById(String id) {
EntityManager em = ThreadLocalContext.get().getEntityManager();
try {
return em.find(FileShare.class, id);
} catch (NoResultException e) {
return null;
}
}
/**
* Get file shares by file ID.
*
* @param fileId File ID
* @return List of file shares
*/
@SuppressWarnings("unchecked")
public List<FileShare> getByFileId(String fileId) {
EntityManager em = ThreadLocalContext.get().getEntityManager();
Query q = em.createQuery("select fs from FileShare fs where fs.fileId = :fileId and fs.deleteDate is null");
q.setParameter("fileId", fileId);
return q.getResultList();
}
}

View File

@ -0,0 +1,113 @@
package com.sismics.docs.core.dao.jpa;
import java.util.Date;
import java.util.List;
import java.util.UUID;
import javax.persistence.EntityManager;
import javax.persistence.NoResultException;
import javax.persistence.Query;
import com.sismics.docs.core.model.jpa.Document;
import com.sismics.docs.core.model.jpa.Share;
import com.sismics.util.context.ThreadLocalContext;
/**
* Share DAO.
*
* @author bgamard
*/
public class ShareDao {
/**
* Creates a new share.
*
* @param share Share
* @return New ID
* @throws Exception
*/
public String create(Share share) {
// Create the UUID
share.setId(UUID.randomUUID().toString());
// Create the share
EntityManager em = ThreadLocalContext.get().getEntityManager();
share.setCreateDate(new Date());
em.persist(share);
return share.getId();
}
/**
* Returns an active share.
*
* @param id Share ID
* @return Document
*/
public Share getShare(String id) {
EntityManager em = ThreadLocalContext.get().getEntityManager();
Query q = em.createQuery("select s from Share s where s.id = :id and s.deleteDate is null");
q.setParameter("id", id);
try {
return (Share) q.getSingleResult();
} catch (NoResultException e) {
return null;
}
}
/**
* Deletes a share.
*
* @param id Share ID
*/
public void delete(String id) {
EntityManager em = ThreadLocalContext.get().getEntityManager();
// Get the share
Query q = em.createQuery("select s from Share s where s.id = :id and s.deleteDate is null");
q.setParameter("id", id);
Share shareDb = (Share) q.getSingleResult();
// Delete the share
Date dateNow = new Date();
shareDb.setDeleteDate(dateNow);
}
/**
* Get shares by document ID.
*
* @param documentId Document ID
* @return List of shares
*/
@SuppressWarnings("unchecked")
public List<Share> getByDocumentId(String documentId) {
EntityManager em = ThreadLocalContext.get().getEntityManager();
Query q = em.createQuery("select s from Share s where s.documentId = :documentId and s.deleteDate is null");
q.setParameter("documentId", documentId);
return q.getResultList();
}
/**
* Check if a document is visible.
*
* @param document Document to check for visibility
* @param userId Optional user trying to access the document
* @param shareId Optional share to access the document
* @return True if the document is visible
*/
public boolean checkVisibility(Document document, String userId, String shareId) {
// The user owns the document
if (document.getUserId().equals(userId)) {
return true;
}
// The share is linked to the document
if (shareId != null) {
Share share = getShare(shareId);
if (share.getDocumentId().equals(document.getId())) {
return true;
}
}
return false;
}
}

View File

@ -1,83 +0,0 @@
package com.sismics.docs.core.model.jpa;
import com.google.common.base.Objects;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.Table;
import java.util.Date;
/**
* File share.
*
* @author bgamard
*/
@Entity
@Table(name = "T_FILESHARE")
public class FileShare {
/**
* File share ID.
*/
@Id
@Column(name = "FSH_ID_C", length = 36)
private String id;
/**
* File ID.
*/
@Column(name = "FSH_IDFILE_C", nullable = false, length = 36)
private String fileId;
/**
* Creation date.
*/
@Column(name = "FSH_CREATEDATE_D", nullable = false)
private Date createDate;
/**
* Deletion date.
*/
@Column(name = "FSH_DELETEDATE_D")
private Date deleteDate;
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getFileId() {
return fileId;
}
public void setFileId(String fileId) {
this.fileId = fileId;
}
public Date getCreateDate() {
return createDate;
}
public void setCreateDate(Date createDate) {
this.createDate = createDate;
}
public Date getDeleteDate() {
return deleteDate;
}
public void setDeleteDate(Date deleteDate) {
this.deleteDate = deleteDate;
}
@Override
public String toString() {
return Objects.toStringHelper(this)
.add("id", id)
.add("tagId", fileId)
.toString();
}
}

View File

@ -0,0 +1,144 @@
package com.sismics.docs.core.model.jpa;
import com.google.common.base.Objects;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.Table;
import java.util.Date;
/**
* File share.
*
* @author bgamard
*/
@Entity
@Table(name = "T_SHARE")
public class Share {
/**
* Share ID.
*/
@Id
@Column(name = "SHA_ID_C", length = 36)
private String id;
@Column(name = "SHA_NAME_C", length = 36)
private String name;
/**
* Document ID.
*/
@Column(name = "SHA_IDDOCUMENT_C", nullable = false, length = 36)
private String documentId;
/**
* Creation date.
*/
@Column(name = "SHA_CREATEDATE_D", nullable = false)
private Date createDate;
/**
* Deletion date.
*/
@Column(name = "SHA_DELETEDATE_D")
private Date deleteDate;
/**
* Getter of id.
*
* @return the id
*/
public String getId() {
return id;
}
/**
* Setter of id.
*
* @param id id
*/
public void setId(String id) {
this.id = id;
}
/**
* Getter of name.
*
* @return the name
*/
public String getName() {
return name;
}
/**
* Setter of name.
*
* @param name name
*/
public void setName(String name) {
this.name = name;
}
/**
* Getter of documentId.
*
* @return the documentId
*/
public String getDocumentId() {
return documentId;
}
/**
* Setter of documentId.
*
* @param documentId documentId
*/
public void setDocumentId(String documentId) {
this.documentId = documentId;
}
/**
* Getter of createDate.
*
* @return the createDate
*/
public Date getCreateDate() {
return createDate;
}
/**
* Setter of createDate.
*
* @param createDate createDate
*/
public void setCreateDate(Date createDate) {
this.createDate = createDate;
}
/**
* Getter of deleteDate.
*
* @return the deleteDate
*/
public Date getDeleteDate() {
return deleteDate;
}
/**
* Setter of deleteDate.
*
* @param deleteDate deleteDate
*/
public void setDeleteDate(Date deleteDate) {
this.deleteDate = deleteDate;
}
@Override
public String toString() {
return Objects.toStringHelper(this)
.add("id", id)
.add("tagId", documentId)
.toString();
}
}

View File

@ -15,6 +15,6 @@
<class>com.sismics.docs.core.model.jpa.Document</class> <class>com.sismics.docs.core.model.jpa.Document</class>
<class>com.sismics.docs.core.model.jpa.Tag</class> <class>com.sismics.docs.core.model.jpa.Tag</class>
<class>com.sismics.docs.core.model.jpa.DocumentTag</class> <class>com.sismics.docs.core.model.jpa.DocumentTag</class>
<class>com.sismics.docs.core.model.jpa.FileShare</class> <class>com.sismics.docs.core.model.jpa.Share</class>
</persistence-unit> </persistence-unit>
</persistence> </persistence>

View File

@ -1 +1 @@
create cached table T_FILESHARE ( FSH_ID_C varchar(36) not null, FSH_IDFILE_C varchar(36) not null, FSH_CREATEDATE_D datetime, FSH_DELETEDATE_D datetime, primary key (FSH_ID_C) ); create cached table T_SHARE ( SHA_ID_C varchar(36) not null, SHA_NAME_C varchar(36), SHA_IDDOCUMENT_C varchar(36) not null, SHA_CREATEDATE_D datetime, SHA_DELETEDATE_D datetime, primary key (SHA_ID_C) );

View File

@ -1,2 +1 @@
- Share a file with a link (client) - Share a document with a link (client)
- Add a label to a file share

View File

@ -1,12 +1,38 @@
package com.sismics.docs.rest.resource; package com.sismics.docs.rest.resource;
import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import javax.persistence.NoResultException;
import javax.ws.rs.DELETE;
import javax.ws.rs.FormParam;
import javax.ws.rs.GET;
import javax.ws.rs.POST;
import javax.ws.rs.PUT;
import javax.ws.rs.Path;
import javax.ws.rs.PathParam;
import javax.ws.rs.Produces;
import javax.ws.rs.QueryParam;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import org.apache.commons.lang.StringUtils;
import org.codehaus.jettison.json.JSONException;
import org.codehaus.jettison.json.JSONObject;
import com.google.common.base.Strings; import com.google.common.base.Strings;
import com.sismics.docs.core.dao.jpa.DocumentDao; import com.sismics.docs.core.dao.jpa.DocumentDao;
import com.sismics.docs.core.dao.jpa.ShareDao;
import com.sismics.docs.core.dao.jpa.TagDao; import com.sismics.docs.core.dao.jpa.TagDao;
import com.sismics.docs.core.dao.jpa.criteria.DocumentCriteria; import com.sismics.docs.core.dao.jpa.criteria.DocumentCriteria;
import com.sismics.docs.core.dao.jpa.dto.DocumentDto; import com.sismics.docs.core.dao.jpa.dto.DocumentDto;
import com.sismics.docs.core.dao.jpa.dto.TagDto; import com.sismics.docs.core.dao.jpa.dto.TagDto;
import com.sismics.docs.core.model.jpa.Document; import com.sismics.docs.core.model.jpa.Document;
import com.sismics.docs.core.model.jpa.Share;
import com.sismics.docs.core.model.jpa.Tag; import com.sismics.docs.core.model.jpa.Tag;
import com.sismics.docs.core.util.jpa.PaginatedList; import com.sismics.docs.core.util.jpa.PaginatedList;
import com.sismics.docs.core.util.jpa.PaginatedLists; import com.sismics.docs.core.util.jpa.PaginatedLists;
@ -14,16 +40,6 @@ import com.sismics.docs.core.util.jpa.SortCriteria;
import com.sismics.rest.exception.ClientException; import com.sismics.rest.exception.ClientException;
import com.sismics.rest.exception.ForbiddenClientException; import com.sismics.rest.exception.ForbiddenClientException;
import com.sismics.rest.util.ValidationUtil; import com.sismics.rest.util.ValidationUtil;
import org.apache.commons.lang.StringUtils;
import org.codehaus.jettison.json.JSONException;
import org.codehaus.jettison.json.JSONObject;
import javax.persistence.NoResultException;
import javax.ws.rs.*;
import javax.ws.rs.core.MediaType;
import javax.ws.rs.core.Response;
import java.text.MessageFormat;
import java.util.*;
/** /**
* Document REST resources. * Document REST resources.
@ -43,15 +59,20 @@ public class DocumentResource extends BaseResource {
@Path("{id: [a-z0-9\\-]+}") @Path("{id: [a-z0-9\\-]+}")
@Produces(MediaType.APPLICATION_JSON) @Produces(MediaType.APPLICATION_JSON)
public Response get( public Response get(
@PathParam("id") String id) throws JSONException { @PathParam("id") String id,
if (!authenticate()) { @QueryParam("share") String shareId) throws JSONException {
throw new ForbiddenClientException(); authenticate();
}
DocumentDao documentDao = new DocumentDao(); DocumentDao documentDao = new DocumentDao();
ShareDao shareDao = new ShareDao();
Document documentDb; Document documentDb;
try { try {
documentDb = documentDao.getDocument(id, principal.getId()); documentDb = documentDao.getDocument(id);
// Check document visibility
if (!shareDao.checkVisibility(documentDb, principal.getId(), shareId)) {
throw new ForbiddenClientException();
}
} catch (NoResultException e) { } catch (NoResultException e) {
throw new ClientException("DocumentNotFound", MessageFormat.format("Document not found: {0}", id)); throw new ClientException("DocumentNotFound", MessageFormat.format("Document not found: {0}", id));
} }
@ -62,7 +83,7 @@ public class DocumentResource extends BaseResource {
document.put("description", documentDb.getDescription()); document.put("description", documentDb.getDescription());
document.put("create_date", documentDb.getCreateDate().getTime()); document.put("create_date", documentDb.getCreateDate().getTime());
// Get tags // Add tags
TagDao tagDao = new TagDao(); TagDao tagDao = new TagDao();
List<TagDto> tagDtoList = tagDao.getByDocumentId(id); List<TagDto> tagDtoList = tagDao.getByDocumentId(id);
List<JSONObject> tags = new ArrayList<>(); List<JSONObject> tags = new ArrayList<>();
@ -75,6 +96,17 @@ public class DocumentResource extends BaseResource {
} }
document.put("tags", tags); document.put("tags", tags);
// Add shares
List<Share> shareDbList = shareDao.getByDocumentId(id);
List<JSONObject> shareList = new ArrayList<>();
for (Share shareDb : shareDbList) {
JSONObject share = new JSONObject();
share.put("id", shareDb.getId());
share.put("name", shareDb.getName());
shareList.add(share);
}
document.put("shares", shareList);
return Response.ok().entity(document).build(); return Response.ok().entity(document).build();
} }

View File

@ -28,10 +28,9 @@ import org.codehaus.jettison.json.JSONObject;
import com.sismics.docs.core.dao.jpa.DocumentDao; import com.sismics.docs.core.dao.jpa.DocumentDao;
import com.sismics.docs.core.dao.jpa.FileDao; import com.sismics.docs.core.dao.jpa.FileDao;
import com.sismics.docs.core.dao.jpa.FileShareDao; import com.sismics.docs.core.dao.jpa.ShareDao;
import com.sismics.docs.core.model.jpa.Document; import com.sismics.docs.core.model.jpa.Document;
import com.sismics.docs.core.model.jpa.File; import com.sismics.docs.core.model.jpa.File;
import com.sismics.docs.core.model.jpa.FileShare;
import com.sismics.docs.core.util.DirectoryUtil; import com.sismics.docs.core.util.DirectoryUtil;
import com.sismics.rest.exception.ClientException; import com.sismics.rest.exception.ClientException;
import com.sismics.rest.exception.ForbiddenClientException; import com.sismics.rest.exception.ForbiddenClientException;
@ -50,52 +49,6 @@ import com.sun.jersey.multipart.FormDataParam;
*/ */
@Path("/file") @Path("/file")
public class FileResource extends BaseResource { public class FileResource extends BaseResource {
/**
* Returns a file.
*
* @param id Document ID
* @return Response
* @throws JSONException
*/
@GET
@Path("{id: [a-z0-9\\-]+}")
@Produces(MediaType.APPLICATION_JSON)
public Response get(
@PathParam("id") String id) throws JSONException {
if (!authenticate()) {
throw new ForbiddenClientException();
}
FileDao fileDao = new FileDao();
FileShareDao fileShareDao = new FileShareDao();
DocumentDao documentDao = new DocumentDao();
File fileDb;
try {
fileDb = fileDao.getFile(id);
documentDao.getDocument(fileDb.getDocumentId(), principal.getId());
} catch (NoResultException e) {
throw new ClientException("FileNotFound", MessageFormat.format("File not found: {0}", id));
}
JSONObject file = new JSONObject();
file.put("id", fileDb.getId());
file.put("mimetype", fileDb.getMimeType());
file.put("document_id", fileDb.getDocumentId());
file.put("create_date", fileDb.getCreateDate().getTime());
// Add file shares
List<FileShare> fileShareDbList = fileShareDao.getByFileId(id);
List<JSONObject> fileShareList = new ArrayList<>();
for (FileShare fileShareDb : fileShareDbList) {
JSONObject fileShare = new JSONObject();
fileShare.put("id", fileShareDb.getId());
fileShareList.add(fileShare);
}
file.put("shares", fileShareList);
return Response.ok().entity(file).build();
}
/** /**
* Add a file to a document. * Add a file to a document.
* *
@ -224,8 +177,15 @@ public class FileResource extends BaseResource {
@Path("list") @Path("list")
@Produces(MediaType.APPLICATION_JSON) @Produces(MediaType.APPLICATION_JSON)
public Response list( public Response list(
@QueryParam("id") String documentId) throws JSONException { @QueryParam("id") String documentId,
if (!authenticate()) { @QueryParam("share") String shareId) throws JSONException {
authenticate();
// Check document visibility
DocumentDao documentDao = new DocumentDao();
Document document = documentDao.getDocument(documentId);
ShareDao shareDao = new ShareDao();
if (!shareDao.checkVisibility(document, principal.getId(), shareId)) {
throw new ForbiddenClientException(); throw new ForbiddenClientException();
} }
@ -297,21 +257,9 @@ public class FileResource extends BaseResource {
@Produces(MediaType.APPLICATION_OCTET_STREAM) @Produces(MediaType.APPLICATION_OCTET_STREAM)
public Response data( public Response data(
@PathParam("id") final String fileId, @PathParam("id") final String fileId,
@QueryParam("share") String fileShareId, @QueryParam("share") String shareId,
@QueryParam("thumbnail") boolean thumbnail) throws JSONException { @QueryParam("thumbnail") boolean thumbnail) throws JSONException {
// Handle file sharing authenticate();
FileShareDao fileShareDao = new FileShareDao();
if (fileShareId != null) {
FileShare fileShare = fileShareDao.getFileShare(fileShareId);
if (fileShare == null) {
throw new ClientException("FileShareNotFound", "File share not found");
}
if (!fileShare.getFileId().equals(fileId)) {
throw new ClientException("InvalidFile", "This file share is not linked to this file");
}
} else if (!authenticate()) {
throw new ForbiddenClientException();
}
// Get the file // Get the file
FileDao fileDao = new FileDao(); FileDao fileDao = new FileDao();
@ -319,8 +267,12 @@ public class FileResource extends BaseResource {
File file; File file;
try { try {
file = fileDao.getFile(fileId); file = fileDao.getFile(fileId);
if (fileShareId == null) { Document document = documentDao.getDocument(file.getDocumentId());
documentDao.getDocument(file.getDocumentId(), principal.getId());
// Check document visibility
ShareDao shareDao = new ShareDao();
if (!shareDao.checkVisibility(document, principal.getId(), shareId)) {
throw new ForbiddenClientException();
} }
} catch (NoResultException e) { } catch (NoResultException e) {
throw new ClientException("FileNotFound", MessageFormat.format("File not found: {0}", fileId)); throw new ClientException("FileNotFound", MessageFormat.format("File not found: {0}", fileId));

View File

@ -17,67 +17,65 @@ import org.codehaus.jettison.json.JSONException;
import org.codehaus.jettison.json.JSONObject; import org.codehaus.jettison.json.JSONObject;
import com.sismics.docs.core.dao.jpa.DocumentDao; import com.sismics.docs.core.dao.jpa.DocumentDao;
import com.sismics.docs.core.dao.jpa.FileDao; import com.sismics.docs.core.dao.jpa.ShareDao;
import com.sismics.docs.core.dao.jpa.FileShareDao; import com.sismics.docs.core.model.jpa.Share;
import com.sismics.docs.core.model.jpa.File;
import com.sismics.docs.core.model.jpa.FileShare;
import com.sismics.rest.exception.ClientException; import com.sismics.rest.exception.ClientException;
import com.sismics.rest.exception.ForbiddenClientException; import com.sismics.rest.exception.ForbiddenClientException;
import com.sismics.rest.util.ValidationUtil; import com.sismics.rest.util.ValidationUtil;
/** /**
* File share REST resources. * Share REST resources.
* *
* @author bgamard * @author bgamard
*/ */
@Path("/fileshare") @Path("/share")
public class FileShareResource extends BaseResource { public class ShareResource extends BaseResource {
/** /**
* Add a file share to a file. * Add a share to a document.
* *
* @param fileId File ID * @param documentId Document ID
* @param fileBodyPart File to add
* @return Response * @return Response
* @throws JSONException * @throws JSONException
*/ */
@PUT @PUT
@Produces(MediaType.APPLICATION_JSON) @Produces(MediaType.APPLICATION_JSON)
public Response add( public Response add(
@FormParam("id") String fileId) throws JSONException { @FormParam("id") String documentId,
@FormParam("name") String name) throws JSONException {
if (!authenticate()) { if (!authenticate()) {
throw new ForbiddenClientException(); throw new ForbiddenClientException();
} }
// Validate input data // Validate input data
ValidationUtil.validateRequired(fileId, "id"); ValidationUtil.validateRequired(documentId, "id");
name = ValidationUtil.validateLength(name, "name", 1, 36, true);
// Get the file // Get the document
FileDao fileDao = new FileDao();
DocumentDao documentDao = new DocumentDao(); DocumentDao documentDao = new DocumentDao();
try { try {
File file = fileDao.getFile(fileId); documentDao.getDocument(documentId, principal.getId());
documentDao.getDocument(file.getDocumentId(), principal.getId());
} catch (NoResultException e) { } catch (NoResultException e) {
throw new ClientException("FileNotFound", MessageFormat.format("File not found: {0}", fileId)); throw new ClientException("DocumentNotFound", MessageFormat.format("Document not found: {0}", documentId));
} }
// Create the file share // Create the share
FileShareDao fileShareDao = new FileShareDao(); ShareDao shareDao = new ShareDao();
FileShare fileShare = new FileShare(); Share share = new Share();
fileShare.setFileId(fileId); share.setDocumentId(documentId);
fileShareDao.create(fileShare); share.setName(name);
shareDao.create(share);
// Always return ok // Always return ok
JSONObject response = new JSONObject(); JSONObject response = new JSONObject();
response.put("status", "ok"); response.put("status", "ok");
response.put("id", fileShare.getId()); response.put("id", share.getId());
return Response.ok().entity(response).build(); return Response.ok().entity(response).build();
} }
/** /**
* Deletes a file share. * Deletes a share.
* *
* @param id File share ID * @param id Share ID
* @return Response * @return Response
* @throws JSONException * @throws JSONException
*/ */
@ -90,21 +88,19 @@ public class FileShareResource extends BaseResource {
throw new ForbiddenClientException(); throw new ForbiddenClientException();
} }
// Get the file share // Get the share
FileShareDao fileShareDao = new FileShareDao(); ShareDao shareDao = new ShareDao();
FileDao fileDao = new FileDao();
DocumentDao documentDao = new DocumentDao(); DocumentDao documentDao = new DocumentDao();
FileShare fileShare; Share share;
try { try {
fileShare = fileShareDao.getFileShare(id); share = shareDao.getShare(id);
File file = fileDao.getFile(fileShare.getFileId()); documentDao.getDocument(share.getDocumentId(), principal.getId());
documentDao.getDocument(file.getDocumentId(), principal.getId());
} catch (NoResultException e) { } catch (NoResultException e) {
throw new ClientException("FileShareNotFound", MessageFormat.format("File share not found: {0}", id)); throw new ClientException("ShareNotFound", MessageFormat.format("Share not found: {0}", id));
} }
// Delete the file share // Delete the share
fileShareDao.delete(fileShare.getId()); shareDao.delete(share.getId());
// Always return ok // Always return ok
JSONObject response = new JSONObject(); JSONObject response = new JSONObject();

View File

@ -1,22 +1,24 @@
package com.sismics.docs.rest; package com.sismics.docs.rest;
import java.io.BufferedInputStream;
import java.io.InputStream;
import javax.ws.rs.core.MediaType;
import junit.framework.Assert;
import org.codehaus.jettison.json.JSONArray;
import org.codehaus.jettison.json.JSONObject;
import org.junit.Test;
import com.google.common.io.ByteStreams; import com.google.common.io.ByteStreams;
import com.sismics.docs.rest.filter.CookieAuthenticationFilter; import com.sismics.docs.rest.filter.CookieAuthenticationFilter;
import com.sismics.util.mime.MimeType;
import com.sun.jersey.api.client.ClientResponse; import com.sun.jersey.api.client.ClientResponse;
import com.sun.jersey.api.client.ClientResponse.Status; import com.sun.jersey.api.client.ClientResponse.Status;
import com.sun.jersey.api.client.WebResource; import com.sun.jersey.api.client.WebResource;
import com.sun.jersey.core.util.MultivaluedMapImpl; import com.sun.jersey.core.util.MultivaluedMapImpl;
import com.sun.jersey.multipart.FormDataBodyPart; import com.sun.jersey.multipart.FormDataBodyPart;
import com.sun.jersey.multipart.FormDataMultiPart; import com.sun.jersey.multipart.FormDataMultiPart;
import junit.framework.Assert;
import org.codehaus.jettison.json.JSONArray;
import org.codehaus.jettison.json.JSONObject;
import org.junit.Test;
import javax.ws.rs.core.MediaType;
import java.io.BufferedInputStream;
import java.io.InputStream;
/** /**
* Exhaustive test of the file resource. * Exhaustive test of the file resource.
@ -76,15 +78,6 @@ public class TestFileResource extends BaseJerseyTest {
json = response.getEntity(JSONObject.class); json = response.getEntity(JSONObject.class);
String file2Id = json.getString("id"); String file2Id = json.getString("id");
// Get the file
fileResource = resource().path("/file/" + file1Id);
fileResource.addFilter(new CookieAuthenticationFilter(file1AuthenticationToken));
response = fileResource.get(ClientResponse.class);
json = response.getEntity(JSONObject.class);
Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus()));
Assert.assertEquals(MimeType.IMAGE_JPEG, json.getString("mimetype"));
Assert.assertEquals(file1Id, json.getString("id"));
// Get the file data // Get the file data
fileResource = resource().path("/file/" + file1Id + "/data"); fileResource = resource().path("/file/" + file1Id + "/data");
fileResource.addFilter(new CookieAuthenticationFilter(file1AuthenticationToken)); fileResource.addFilter(new CookieAuthenticationFilter(file1AuthenticationToken));

View File

@ -7,6 +7,7 @@ import javax.ws.rs.core.MediaType;
import junit.framework.Assert; import junit.framework.Assert;
import org.codehaus.jettison.json.JSONArray;
import org.codehaus.jettison.json.JSONObject; import org.codehaus.jettison.json.JSONObject;
import org.junit.Test; import org.junit.Test;
@ -20,25 +21,25 @@ import com.sun.jersey.multipart.FormDataBodyPart;
import com.sun.jersey.multipart.FormDataMultiPart; import com.sun.jersey.multipart.FormDataMultiPart;
/** /**
* Exhaustive test of the file share resource. * Exhaustive test of the share resource.
* *
* @author bgamard * @author bgamard
*/ */
public class TestFileShareResource extends BaseJerseyTest { public class TestShareResource extends BaseJerseyTest {
/** /**
* Test the file share resource. * Test the share resource.
* *
* @throws Exception * @throws Exception
*/ */
@Test @Test
public void testFileShareResource() throws Exception { public void testShareResource() throws Exception {
// Login fileshare1 // Login share1
clientUtil.createUser("fileshare1"); clientUtil.createUser("share1");
String fileShare1AuthenticationToken = clientUtil.login("fileshare1"); String share1AuthenticationToken = clientUtil.login("share1");
// Create a document // Create a document
WebResource documentResource = resource().path("/document"); WebResource documentResource = resource().path("/document");
documentResource.addFilter(new CookieAuthenticationFilter(fileShare1AuthenticationToken)); documentResource.addFilter(new CookieAuthenticationFilter(share1AuthenticationToken));
MultivaluedMapImpl postParams = new MultivaluedMapImpl(); MultivaluedMapImpl postParams = new MultivaluedMapImpl();
postParams.add("title", "File test document 1"); postParams.add("title", "File test document 1");
ClientResponse response = documentResource.put(ClientResponse.class, postParams); ClientResponse response = documentResource.put(ClientResponse.class, postParams);
@ -49,7 +50,7 @@ public class TestFileShareResource extends BaseJerseyTest {
// Add a file // Add a file
WebResource fileResource = resource().path("/file"); WebResource fileResource = resource().path("/file");
fileResource.addFilter(new CookieAuthenticationFilter(fileShare1AuthenticationToken)); fileResource.addFilter(new CookieAuthenticationFilter(share1AuthenticationToken));
FormDataMultiPart form = new FormDataMultiPart(); FormDataMultiPart form = new FormDataMultiPart();
InputStream file = this.getClass().getResourceAsStream("/file/PIA00452.jpg"); InputStream file = this.getClass().getResourceAsStream("/file/PIA00452.jpg");
FormDataBodyPart fdp = new FormDataBodyPart("file", FormDataBodyPart fdp = new FormDataBodyPart("file",
@ -62,40 +63,54 @@ public class TestFileShareResource extends BaseJerseyTest {
json = response.getEntity(JSONObject.class); json = response.getEntity(JSONObject.class);
String file1Id = json.getString("id"); String file1Id = json.getString("id");
// Share this file // Share this document
WebResource fileShareResource = resource().path("/fileshare"); WebResource fileShareResource = resource().path("/share");
fileShareResource.addFilter(new CookieAuthenticationFilter(fileShare1AuthenticationToken)); fileShareResource.addFilter(new CookieAuthenticationFilter(share1AuthenticationToken));
postParams = new MultivaluedMapImpl(); postParams = new MultivaluedMapImpl();
postParams.add("id", file1Id); postParams.add("id", document1Id);
postParams.add("name", "4 All");
response = fileShareResource.put(ClientResponse.class, postParams); response = fileShareResource.put(ClientResponse.class, postParams);
Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus())); Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus()));
json = response.getEntity(JSONObject.class); json = response.getEntity(JSONObject.class);
String fileShare1Id = json.getString("id"); String share1Id = json.getString("id");
// Get the document anonymously
documentResource = resource().path("/document/" + document1Id);
MultivaluedMapImpl getParams = new MultivaluedMapImpl();
getParams.putSingle("share", share1Id);
response = documentResource.queryParams(getParams).get(ClientResponse.class);
json = response.getEntity(JSONObject.class);
Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus()));
Assert.assertEquals(document1Id, json.getString("id"));
Assert.assertEquals(1, json.getJSONArray("shares").length());
Assert.assertEquals(share1Id, json.getJSONArray("shares").getJSONObject(0).getString("id"));
Assert.assertEquals("4 All", json.getJSONArray("shares").getJSONObject(0).getString("name"));
// Get all files from this document anonymously
fileResource = resource().path("/file/list");
getParams = new MultivaluedMapImpl();
getParams.putSingle("id", document1Id);
getParams.putSingle("share", share1Id);
response = fileResource.queryParams(getParams).get(ClientResponse.class);
json = response.getEntity(JSONObject.class);
Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus()));
JSONArray files = json.getJSONArray("files");
Assert.assertEquals(1, files.length());
// Get the file data anonymously // Get the file data anonymously
fileResource = resource().path("/file/" + file1Id + "/data"); fileResource = resource().path("/file/" + file1Id + "/data");
MultivaluedMapImpl getParams = new MultivaluedMapImpl(); getParams = new MultivaluedMapImpl();
getParams.putSingle("thumbnail", false); getParams.putSingle("thumbnail", false);
getParams.putSingle("share", fileShare1Id); getParams.putSingle("share", share1Id);
response = fileResource.queryParams(getParams).get(ClientResponse.class); response = fileResource.queryParams(getParams).get(ClientResponse.class);
Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus())); Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus()));
InputStream is = response.getEntityInputStream(); InputStream is = response.getEntityInputStream();
byte[] fileBytes = ByteStreams.toByteArray(is); byte[] fileBytes = ByteStreams.toByteArray(is);
Assert.assertEquals(163510, fileBytes.length); Assert.assertEquals(163510, fileBytes.length);
// Get the file
fileResource = resource().path("/file/" + file1Id);
fileResource.addFilter(new CookieAuthenticationFilter(fileShare1AuthenticationToken));
response = fileResource.get(ClientResponse.class);
json = response.getEntity(JSONObject.class);
Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus()));
Assert.assertEquals(file1Id, json.getString("id"));
Assert.assertEquals(1, json.getJSONArray("shares").length());
Assert.assertEquals(fileShare1Id, json.getJSONArray("shares").getJSONObject(0).getString("id"));
// Deletes the share // Deletes the share
fileShareResource = resource().path("/fileshare/" + fileShare1Id); fileShareResource = resource().path("/share/" + share1Id);
fileShareResource.addFilter(new CookieAuthenticationFilter(fileShare1AuthenticationToken)); fileShareResource.addFilter(new CookieAuthenticationFilter(share1AuthenticationToken));
response = fileShareResource.delete(ClientResponse.class); response = fileShareResource.delete(ClientResponse.class);
Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus())); Assert.assertEquals(Status.OK, Status.fromStatusCode(response.getStatus()));
json = response.getEntity(JSONObject.class); json = response.getEntity(JSONObject.class);