Google Integration:

- Version history of googleeditable content is now correct
  - You can now upload new content to a googleeditable content node (previously the uploaded content was over written)
  


git-svn-id: https://svn.alfresco.com/repos/alfresco-enterprise/alfresco/HEAD/root@20333 c4b6b30b-aa2e-2d43-bbcb-ca4b014f7261
This commit is contained in:
Roy Wetherall
2010-05-21 13:47:23 +00:00
parent d2a4743e80
commit 24e435a11e
2 changed files with 114 additions and 38 deletions

View File

@@ -64,6 +64,7 @@ import com.google.gdata.data.acl.AclScope;
import com.google.gdata.data.docs.DocumentEntry; import com.google.gdata.data.docs.DocumentEntry;
import com.google.gdata.data.docs.DocumentListEntry; import com.google.gdata.data.docs.DocumentListEntry;
import com.google.gdata.data.docs.FolderEntry; import com.google.gdata.data.docs.FolderEntry;
import com.google.gdata.data.docs.PdfEntry;
import com.google.gdata.data.docs.PresentationEntry; import com.google.gdata.data.docs.PresentationEntry;
import com.google.gdata.data.docs.SpreadsheetEntry; import com.google.gdata.data.docs.SpreadsheetEntry;
import com.google.gdata.data.docs.DocumentListEntry.MediaType; import com.google.gdata.data.docs.DocumentListEntry.MediaType;
@@ -736,6 +737,10 @@ public class GoogleDocsServiceImpl extends TransactionListenerAdapter
{ {
docEntry = new PresentationEntry(); docEntry = new PresentationEntry();
} }
else if (MediaType.PDF.getMimeType().equals(mimetype) == true)
{
docEntry = new PdfEntry();
}
else else
{ {
docEntry = new DocumentEntry(); docEntry = new DocumentEntry();

View File

@@ -19,24 +19,34 @@
package org.alfresco.repo.googledocs; package org.alfresco.repo.googledocs;
import java.io.InputStream; import java.io.InputStream;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import org.alfresco.error.AlfrescoRuntimeException; import org.alfresco.error.AlfrescoRuntimeException;
import org.alfresco.model.ContentModel; import org.alfresco.model.ContentModel;
import org.alfresco.repo.coci.CheckOutCheckInServicePolicies; import org.alfresco.repo.coci.CheckOutCheckInServicePolicies;
import org.alfresco.repo.coci.CheckOutCheckInServicePolicies.BeforeCancelCheckOut; import org.alfresco.repo.coci.CheckOutCheckInServicePolicies.BeforeCheckIn;
import org.alfresco.repo.coci.CheckOutCheckInServicePolicies.OnCheckIn; import org.alfresco.repo.coci.CheckOutCheckInServicePolicies.OnCheckIn;
import org.alfresco.repo.coci.CheckOutCheckInServicePolicies.OnCheckOut; import org.alfresco.repo.coci.CheckOutCheckInServicePolicies.OnCheckOut;
import org.alfresco.repo.copy.CopyBehaviourCallback;
import org.alfresco.repo.copy.CopyDetails;
import org.alfresco.repo.copy.DefaultCopyBehaviourCallback;
import org.alfresco.repo.node.NodeServicePolicies; import org.alfresco.repo.node.NodeServicePolicies;
import org.alfresco.repo.node.NodeServicePolicies.BeforeDeleteNodePolicy; import org.alfresco.repo.node.NodeServicePolicies.BeforeDeleteNodePolicy;
import org.alfresco.repo.node.NodeServicePolicies.OnAddAspectPolicy; import org.alfresco.repo.node.NodeServicePolicies.OnAddAspectPolicy;
import org.alfresco.repo.policy.JavaBehaviour; import org.alfresco.repo.policy.JavaBehaviour;
import org.alfresco.repo.policy.PolicyComponent; import org.alfresco.repo.policy.PolicyComponent;
import org.alfresco.repo.policy.Behaviour.NotificationFrequency; import org.alfresco.repo.policy.Behaviour.NotificationFrequency;
import org.alfresco.repo.transaction.AlfrescoTransactionSupport;
import org.alfresco.service.cmr.dictionary.DictionaryService; import org.alfresco.service.cmr.dictionary.DictionaryService;
import org.alfresco.service.cmr.repository.ContentService; import org.alfresco.service.cmr.repository.ContentService;
import org.alfresco.service.cmr.repository.ContentWriter; import org.alfresco.service.cmr.repository.ContentWriter;
import org.alfresco.service.cmr.repository.NodeRef; import org.alfresco.service.cmr.repository.NodeRef;
import org.alfresco.service.cmr.repository.NodeService; import org.alfresco.service.cmr.repository.NodeService;
import org.alfresco.service.namespace.NamespaceService;
import org.alfresco.service.namespace.QName; import org.alfresco.service.namespace.QName;
/** /**
@@ -45,9 +55,8 @@ import org.alfresco.service.namespace.QName;
*/ */
public class GoogleEditableAspect implements NodeServicePolicies.OnAddAspectPolicy, public class GoogleEditableAspect implements NodeServicePolicies.OnAddAspectPolicy,
CheckOutCheckInServicePolicies.OnCheckOut, CheckOutCheckInServicePolicies.OnCheckOut,
CheckOutCheckInServicePolicies.OnCheckIn, CheckOutCheckInServicePolicies.BeforeCheckIn,
NodeServicePolicies.BeforeDeleteNodePolicy NodeServicePolicies.BeforeDeleteNodePolicy
//CheckOutCheckInServicePolicies.BeforeCancelCheckOut
{ {
/** Indicates whether behaviour is enabled or not */ /** Indicates whether behaviour is enabled or not */
boolean enabled = false; boolean enabled = false;
@@ -122,19 +131,31 @@ public class GoogleEditableAspect implements NodeServicePolicies.OnAddAspectPoli
{ {
if (enabled == true) if (enabled == true)
{ {
// Register behaviour with policy component // GoogleEditable resource behaviours
policyComponent.bindClassBehaviour(OnAddAspectPolicy.QNAME, policyComponent.bindClassBehaviour(OnAddAspectPolicy.QNAME,
GoogleDocsModel.ASPECT_GOOGLEEDITABLE , GoogleDocsModel.ASPECT_GOOGLEEDITABLE ,
new JavaBehaviour(this, "onAddAspect", NotificationFrequency.FIRST_EVENT)); new JavaBehaviour(this, "onAddAspect", NotificationFrequency.FIRST_EVENT));
policyComponent.bindClassBehaviour(OnCheckOut.QNAME, policyComponent.bindClassBehaviour(OnCheckOut.QNAME,
GoogleDocsModel.ASPECT_GOOGLEEDITABLE, GoogleDocsModel.ASPECT_GOOGLEEDITABLE,
new JavaBehaviour(this, "onCheckOut", NotificationFrequency.FIRST_EVENT)); new JavaBehaviour(this, "onCheckOut", NotificationFrequency.FIRST_EVENT));
policyComponent.bindClassBehaviour(OnCheckIn.QNAME,
GoogleDocsModel.ASPECT_GOOGLEEDITABLE, // Google resource behaviours
new JavaBehaviour(this, "onCheckIn", NotificationFrequency.FIRST_EVENT)); policyComponent.bindClassBehaviour(BeforeCheckIn.QNAME,
GoogleDocsModel.ASPECT_GOOGLERESOURCE,
new JavaBehaviour(this, "beforeCheckIn", NotificationFrequency.FIRST_EVENT));
policyComponent.bindClassBehaviour(BeforeDeleteNodePolicy.QNAME, policyComponent.bindClassBehaviour(BeforeDeleteNodePolicy.QNAME,
GoogleDocsModel.ASPECT_GOOGLERESOURCE, GoogleDocsModel.ASPECT_GOOGLERESOURCE,
new JavaBehaviour(this, "beforeDeleteNode", NotificationFrequency.FIRST_EVENT)); new JavaBehaviour(this, "beforeDeleteNode", NotificationFrequency.FIRST_EVENT));
// Copy behaviours
this.policyComponent.bindClassBehaviour(
QName.createQName(NamespaceService.ALFRESCO_URI, "getCopyCallback"),
GoogleDocsModel.ASPECT_GOOGLEEDITABLE,
new JavaBehaviour(this, "getGoogleEditableCopyCallback"));
this.policyComponent.bindClassBehaviour(
QName.createQName(NamespaceService.ALFRESCO_URI, "getCopyCallback"),
GoogleDocsModel.ASPECT_GOOGLERESOURCE,
new JavaBehaviour(this, "getGoogleResourceCopyCallback"));
} }
} }
@@ -161,41 +182,65 @@ public class GoogleEditableAspect implements NodeServicePolicies.OnAddAspectPoli
public void onCheckOut(NodeRef workingCopy) public void onCheckOut(NodeRef workingCopy)
{ {
if (nodeService.exists(workingCopy) == true) if (nodeService.exists(workingCopy) == true)
{ {
// Remove the google editable aspect from the working copy
nodeService.removeAspect(workingCopy, GoogleDocsModel.ASPECT_GOOGLEEDITABLE);
// Upload the content of the working copy to google docs // Upload the content of the working copy to google docs
googleDocsService.createGoogleDoc(workingCopy, GoogleDocsPermissionContext.SHARE_WRITE); googleDocsService.createGoogleDoc(workingCopy, GoogleDocsPermissionContext.SHARE_WRITE);
// Mark checkout
markCheckOut(workingCopy);
} }
} }
/** private static final String KEY_CHECKEDOUT = "googleeditableaspect.checkedout";
* @see org.alfresco.repo.coci.CheckOutCheckInServicePolicies.OnCheckIn#onCheckIn(org.alfresco.service.cmr.repository.NodeRef)
*/ private void markCheckOut(NodeRef nodeRef)
public void onCheckIn(NodeRef nodeRef) {
List<NodeRef> resources = (List<NodeRef>)AlfrescoTransactionSupport.getResource(KEY_CHECKEDOUT);
if (resources == null)
{
// bind pending rules to the current transaction
resources = new ArrayList<NodeRef>();
AlfrescoTransactionSupport.bindResource(KEY_CHECKEDOUT, resources);
}
resources.add(nodeRef);
}
private boolean isMarkedCheckOut(NodeRef nodeRef)
{ {
if (nodeService.exists(nodeRef) == true && boolean result = false;
nodeService.hasAspect(nodeRef, GoogleDocsModel.ASPECT_GOOGLERESOURCE) == true) List<NodeRef> resources = (List<NodeRef>)AlfrescoTransactionSupport.getResource(KEY_CHECKEDOUT);
if (resources != null &&
resources.contains(nodeRef) == true)
{
result = true;
}
return result;
}
public void beforeCheckIn(NodeRef workingCopyNodeRef,
Map<String, Serializable> versionProperties, String contentUrl,
boolean keepCheckedOut)
{
if (nodeService.exists(workingCopyNodeRef) == true &&
nodeService.hasAspect(workingCopyNodeRef, GoogleDocsModel.ASPECT_GOOGLERESOURCE) == true &&
isMarkedCheckOut(workingCopyNodeRef) == false)
{ {
// Get input stream for the google doc // Get input stream for the google doc
InputStream is = googleDocsService.getGoogleDocContent(nodeRef); InputStream is = googleDocsService.getGoogleDocContent(workingCopyNodeRef);
if (is == null) if (is == null)
{ {
throw new AlfrescoRuntimeException("Unable to complete check in, because the working copy content could not be retrieved from google docs."); throw new AlfrescoRuntimeException("Unable to complete check in, because the working copy content could not be retrieved from google docs.");
} }
// Write the google content into the node // Write the google content into the node
ContentWriter writer = contentService.getWriter(nodeRef, ContentModel.PROP_CONTENT, true); ContentWriter writer = contentService.getWriter(workingCopyNodeRef, ContentModel.PROP_CONTENT, true);
writer.putContent(is); writer.putContent(is);
}
// Delete the associated google resource
//googleDocsService.deleteGoogleResource(nodeRef);
nodeService.removeAspect(nodeRef, GoogleDocsModel.ASPECT_GOOGLERESOURCE);
}
} }
/**
* @see org.alfresco.repo.node.NodeServicePolicies.BeforeDeleteNodePolicy#beforeDeleteNode(org.alfresco.service.cmr.repository.NodeRef)
*/
public void beforeDeleteNode(NodeRef nodeRef) public void beforeDeleteNode(NodeRef nodeRef)
{ {
if (nodeService.exists(nodeRef) == true) if (nodeService.exists(nodeRef) == true)
@@ -204,16 +249,42 @@ public class GoogleEditableAspect implements NodeServicePolicies.OnAddAspectPoli
googleDocsService.deleteGoogleResource(nodeRef); googleDocsService.deleteGoogleResource(nodeRef);
} }
} }
public CopyBehaviourCallback getGoogleEditableCopyCallback(QName classRef, CopyDetails copyDetails)
{
return GoogleEditableCopyBehaviourCallback.INSTANCE;
}
/** private static class GoogleEditableCopyBehaviourCallback extends DefaultCopyBehaviourCallback
* @see org.alfresco.repo.coci.CheckOutCheckInServicePolicies.BeforeCancelCheckOut#beforeCancelCheckOut(org.alfresco.service.cmr.repository.NodeRef) {
*/ private static final CopyBehaviourCallback INSTANCE = new GoogleEditableCopyBehaviourCallback();
// public void beforeCancelCheckOut(NodeRef workingCopyNodeRef)
// { /**
// if (nodeService.exists(workingCopyNodeRef) == true) * @return Returns an empty map
// { */
// // Delete the associated google resource @Override
// googleDocsService.deleteGoogleResource(workingCopyNodeRef); public Map<QName, Serializable> getCopyProperties(QName classQName, CopyDetails copyDetails, Map<QName, Serializable> properties)
// } {
// } return Collections.emptyMap();
}
}
public CopyBehaviourCallback getGoogleResourceCopyCallback(QName classRef, CopyDetails copyDetails)
{
return GoogleResourceCopyBehaviourCallback.INSTANCE;
}
private static class GoogleResourceCopyBehaviourCallback extends DefaultCopyBehaviourCallback
{
private static final CopyBehaviourCallback INSTANCE = new GoogleEditableCopyBehaviourCallback();
/**
* @return Returns an empty map
*/
@Override
public Map<QName, Serializable> getCopyProperties(QName classQName, CopyDetails copyDetails, Map<QName, Serializable> properties)
{
return Collections.emptyMap();
}
}
} }