I have a list with the requirement to keep a history of a frequently updated multi-line status. Additional requirements are to not show history on New and Edit forms and Views, but to show the history on the Display form. Additionally, the DataSheet view must be able update the field.
I pieces of the implementation are :
- Status: A multi-line text field to be displayed everywhere but the Display form.
- StatusHistory: A multi-line text field with auto-append enabled to be on the Display form.
- StatusPrevious: a hidden multi-line text field used by the workflow
- Designer workflow to check the value of Status against PreviousStatus and update both PreviousStatus and StatusHistory when different.
This works OK, although there are occasionally duplicate or blank entries copied to StatusHistory.
I was moving some other logic into event recievers and thought I would move this as well. This is working as expected, with one problem.
The StatusHistory field is being updated with every save. If the status has not changed, the event reciever doesn't do anything to these fields, but the item version shows the StatusHistory field as being blanked out.
There are other multi-line, auto-appending fields in the list, but they don't insist on updating themselves everytime the item is saved.
The only difference I can see between the StatusHistory and the other multi-line, auto-appending fields is the StatusHistory field is not on the New and Edit form.
Does anyone know why StatusHistory is updating every save (regardless of change); and more importantly, how to stop it from doing so?
After a few more tests:
Status History is updated without change on the version following a version in which it was changed. This image will help make it clear.
In the highlighted versions, the edit form was opened and saved with no changes made. Version 1 had so many default values set in other fields the two I'm interested in were not visible. I entered 'This is the text' in version 1 and added ', revised' in version 4.
It seems some metadata within the field is not getting set, and it thinks it is still empty after having been updated by the event receiver.
This is the code that is called in both the ItemAdding and ItemUpdating event receivers:
private static void AccumulateText(SPItemEventProperties properties, string textFieldName, string textFieldHistoryName)
{
var eodStatusInternalName = GetFieldInternalName(properties, textFieldName);
var eodStatus = properties.AfterProperties[eodStatusInternalName] as string;
var previousEodStatus = string.Empty;
if (properties.ListItem != null)
{
var previousVersion = properties.ListItem.Versions[0];
var field = previousVersion.Fields[textFieldName] as SPFieldMultiLineText;
if (field != null)
{
previousEodStatus = field.GetFieldValueAsText(previousVersion[textFieldName]);
}
}
if (previousEodStatus == eodStatus)
return;
var eodStatusHistoryInternalName = GetFieldInternalName(properties, textFieldHistoryName);
properties.AfterProperties[eodStatusHistoryInternalName] = eodStatus;
}