Tuesday, August 7, 2012

Track SharePoint Attachments Uploaded and Deleted in the EditForm using JavaScript

To track the changes to attachments in a SharePoint item for auditing/record keeping purposes:

1. Create a new SharePoint edit form for the list using SharePoint Designer
2. Make sure that your Edit Form is updated and can upload attachments (use this MSDN article if you are having issues http://support.microsoft.com/kb/953271/en-us)

3. **Updated step**

Find <tr id="idAttachmentsRow" > and directly underneath of that closing </tr> add the following:


<tr style="display:none">
      <td colspan="2" valign="top" class="ms-formbody" nowrap="" height="20px">
       <H3 class="ms-standardheader">
              <SharePoint:AttachmentsField ControlMode="Display" FieldName="Attachments" runat="server" Visible="true"/>
       </H3>
      </td>
     </tr>
(By adding this row and this field, it will retain the name of the attachment)
    
4. To get the newly added attachments, you will want to grab the "attachmentsOnClient" element. This is where the references to the newly added attachments are stored. Next, you will want to iterate through all the INPUT tags and get the "value" attribute to get the names of the files that were uploaded.

5. To get the removed attachments from the SharePoint list item, we will grab the "attachmentsToBeRemovedFromServer" element. All of the GUIDs of the list item attachments to be removed are stored in this element. We will parse out each guid and use it to identify the attachmentRow found under the attachmentsTable. This row will have a reference to the removed items.

6. To view the changes that have been made when a user clicks to save the form, add the script below. Of course, instead of alerting the user of the changes made, you can record it in a status or audit trail field to make it more seamless!


 
<script type="text/javascript">

function GetNewlyUploadedAttachments()
{
 var uploadedAttachments = new Array();
 var oAttachments = document.getElementById("attachmentsOnClient");
 if( oAttachments.innerHTML != null )
 {
  var attachmentTable = oAttachments.getElementsByTagName("INPUT");
  for (var i = 0; i < attachmentTable.length; i++) 
  {    
   var value = attachmentTable[i].getAttribute("value");    
   if ( value != null && value.length > 0 ) 
   {   
    var lastIndex = value.lastIndexOf("\\");
    var fileName = value.substring(lastIndex+1);
    uploadedAttachments.push(fileName); 
   } 
  } 
 }

 return uploadedAttachments.toString();
}

function GetRemovedAttachments()
{
 var removedAttachments = new Array();
 var attachmentsToBeRemoved = document.getElementsByName("attachmentsToBeRemovedFromServer").item(0).value;

 if( attachmentsToBeRemoved != null && attachmentsToBeRemoved != "")
 {
  var array = attachmentsToBeRemoved.split(';');
  for(var i =0; i < array.length; i++ )
  {
   attachmentGuid = array[i];
   if( attachmentGuid != null && attachmentGuid != "" )
   {
    var attachmentRow =  document.getElementById(attachmentGuid);
    var span = attachmentRow.getElementsByTagName('span')[0];
    var links = span.getElementsByTagName("a");
    for (z = 0; z < links.length; z++) 
    {
     removedAttachments.push(links[z].firstChild.nodeValue);
    }
   }
  }
 }
 return removedAttachments.toString();
}

function PreSaveAction()
{
 var newUploadedAttachments = GetNewlyUploadedAttachments();
 var removedAttachments = GetRemovedAttachments();
 if( removedAttachments != null && removedAttachments != "" )
 {
  alert("User removed attachments: " + removedAttachments );
 }
 if( newUploadedAttachments != null && newUploadedAttachments != "" )
 {
  alert("User uploaded attachments: " + newUploadedAttachments );
 }
}
</script>



2 comments:

  1. Hi,
    In function GetRemovedAttachments() attachmentRow is always null, because You can't get element with id=attachmentGuid (this row doesn't exist).
    Please tell me if I am wrong.
    Best, Tomek ;)

    ReplyDelete
  2. Gosh, sorry about that! I forgot to add one crucial step. I've updated this blog so please refer to step 3.

    Thanks!

    ReplyDelete