private static void DoSomeProblemWork() { DateTime dtProblemWorkStart = DateTime.Now; int intRadomClassification = Helper.GetRandomNumber(0, listProblemClassificationEnums.Count); ManagementPackEnumeration mpeRandomClassification = listProblemClassificationEnums.ElementAtOrDefault <ManagementPackEnumeration>(intRadomClassification); string strClassificationCriteriaXml = Helper.SearchObjectByEnumerationCriteriaXml(mpeRandomClassification, mpcProblem, mppProblemClassification); IObjectProjectionReader <EnterpriseManagementObject> oprProblemView = Helper.GetBufferedObjectProjectionReader(strClassificationCriteriaXml, intNumberOfWorkItemsToGet, mptpProblemView, emg); if (oprProblemView == null) { Console.WriteLine("No objects to retrieve given the criteria"); } else { //Get a particular problem (full projection) and update it by adding an action log entry and string strProblemId = null; if (oprProblemView.Count > 0) { strProblemId = oprProblemView.ElementAtOrDefault <EnterpriseManagementObjectProjection>(Helper.GetRandomNumber(0, oprProblemView.Count - 1)).Object[mpcProblem, "Id"].Value.ToString(); } if (strProblemId != null) { string strCriteriaXml = Helper.SearchWorkItemByIDCriteriaXml(strProblemId, mpSystemWorkItemLibrary.Name, mpSystemWorkItemLibrary.Version.ToString(), mpSystemWorkItemLibrary.KeyToken, "System.WorkItem"); ObjectProjectionCriteria opcProblemFull = new ObjectProjectionCriteria(strCriteriaXml, mptpProblemFull, emg); IObjectProjectionReader <EnterpriseManagementObject> oprProblemFull = emg.EntityObjects.GetObjectProjectionReader <EnterpriseManagementObject>(opcProblemFull, ObjectQueryOptions.Default); EnterpriseManagementObjectProjection emopProblemFull = oprProblemFull.First <EnterpriseManagementObjectProjection>(); emopProblemFull.Object[mpcProblem, "Description"].Value = Guid.NewGuid().ToString(); int intRandomEnumID = Helper.GetRandomNumber(0, listProblemClassificationEnums.Count); ManagementPackEnumeration mpeClassification = listProblemClassificationEnums.ElementAtOrDefault <ManagementPackEnumeration>(intRandomEnumID); emopProblemFull.Object[mpcProblemExtension, "Classification"].Value = mpeClassification; //EnterpriseManagementObjectCriteria emocComputer = new EnterpriseManagementObjectCriteria(); ObjectQueryOptions oqoComputer = new ObjectQueryOptions(); oqoComputer.MaxResultCount = 5; oqoComputer.DefaultPropertyRetrievalBehavior = ObjectPropertyRetrievalBehavior.All; oqoComputer.ObjectRetrievalMode = ObjectRetrievalOptions.Buffered; IObjectReader <EnterpriseManagementObject> orComputers = emg.EntityObjects.GetObjectReader <EnterpriseManagementObject>(mpcComputer, oqoComputer); if (bSimulateHumanWaitTime) { Thread.Sleep(intDoWorkPause); } emopProblemFull.Overwrite(); DateTime dtProblemWorkEnd = DateTime.Now; TimeSpan tsProblemWork = dtProblemWorkEnd - dtProblemWorkStart; pcProblemWork.RawValue = (long)tsProblemWork.TotalSeconds; Console.WriteLine("Problem work completed (seconds): " + tsProblemWork.TotalSeconds); } } }
public static EnterpriseManagementObject GetUserFromEmailAddress(string strEmailAddress, EnterpriseManagementGroup emg) { strEmailAddress = MakeSafeXML(strEmailAddress); ManagementPack mpSystemNotificationsLibrary = GetManagementPackByName("System.Notifications.Library", emg); ManagementPack mpSystemSupportingItemLibrary = GetManagementPackByName("System.SupportingItem.Library", emg); if (mpSystemNotificationsLibrary != null && mpSystemSupportingItemLibrary != null) { EnterpriseManagementObject emoSCSMUser = null; //Criteria to get a user provided the email address string strCriteria = String.Format(@" <Criteria xmlns=""http://Microsoft.EnterpriseManagement.Core.Criteria/""> <Reference Id=""{0}"" Version=""{1}"" PublicKeyToken=""{2}"" Alias=""NotificationLibrary"" /> <Reference Id=""{3}"" Version=""{4}"" PublicKeyToken=""{5}"" Alias=""SupportingItemLibrary"" /> <Expression> <SimpleExpression> <ValueExpressionLeft> <Property>$Target/Path[Relationship='SupportingItemLibrary!System.UserHasPreference' TypeConstraint='NotificationLibrary!System.Notification.Endpoint']/Property[Type='NotificationLibrary!System.Notification.Endpoint']/TargetAddress$</Property> </ValueExpressionLeft> <Operator>Equal</Operator> <ValueExpressionRight> <Value>{6}</Value> </ValueExpressionRight> </SimpleExpression> </Expression> </Criteria>", mpSystemNotificationsLibrary.Name, mpSystemNotificationsLibrary.Version.ToString(), mpSystemNotificationsLibrary.KeyToken, mpSystemSupportingItemLibrary.Name, mpSystemSupportingItemLibrary.Version.ToString(), mpSystemSupportingItemLibrary.KeyToken, strEmailAddress); ManagementPackTypeProjection mptpUserPreferences = GetTypeProjectionByName("System.User.Preferences.Projection", emg); ObjectProjectionCriteria opcFindNotificationEndPointByEmailAddress = new ObjectProjectionCriteria(strCriteria, mptpUserPreferences, emg); IObjectProjectionReader <EnterpriseManagementObject> readerNotificationEndpoints = emg.EntityObjects.GetObjectProjectionReader <EnterpriseManagementObject>(opcFindNotificationEndPointByEmailAddress, ObjectQueryOptions.Default); foreach (EnterpriseManagementObjectProjection emopNotificationEndpointItem in readerNotificationEndpoints) { emoSCSMUser = emopNotificationEndpointItem.Object; } return(emoSCSMUser); } else { return(null); } }
private void TestGettingIncidentsByEnumCriteria() { EnterpriseManagementGroup emg = new EnterpriseManagementGroup(txtServerName.Text); ManagementPack mpIncidentLibrary = Helper.GetManagementPackByName("System.WorkItem.Incident.Library", emg); ManagementPackClass mpcIncident = Helper.GetClassByName("System.WorkItem.Incident", emg); ManagementPackProperty mppClassification = Helper.GetManagementPackClassPropertyByName("System.WorkItem.Incident", "Classification", emg); ManagementPackTypeProjection mptpIncident = Helper.GetTypeProjectionByName("System.WorkItem.Incident.View.ProjectionType", emg); ManagementPackEnumeration mpeClassificationEnterpriseApp = Helper.GetEnumerationByName("IncidentClassificationEnum.EnterpriseApplications", emg); string strCriteria = Helper.SearchObjectByEnumerationCriteriaXml(mpeClassificationEnterpriseApp, mpcIncident, mppClassification); IObjectProjectionReader <EnterpriseManagementObject> reader = Helper.GetBufferedObjectProjectionReader(strCriteria, 40, mptpIncident, emg); MessageBox.Show(reader.Count.ToString()); }
private static void DoSomeServiceRequestWork() { DateTime dtServiceRequestWorkStart = DateTime.Now; int intRandomAreaEnum = Helper.GetRandomNumber(0, listSRAreaEnums.Count); ManagementPackEnumeration mpeRadomArea = listSRAreaEnums.ElementAtOrDefault <ManagementPackEnumeration>(intRandomAreaEnum); string strCriteria = Helper.SearchObjectByEnumerationCriteriaXml(mpeRadomArea, mpcServiceRequest, mppServiceRequestArea); IObjectProjectionReader <EnterpriseManagementObject> oprServiceRequestsView = Helper.GetBufferedObjectProjectionReader(strCriteria, intNumberOfWorkItemsToGet, mptpServiceRequestView, emg); if (oprServiceRequestsView == null) { Console.WriteLine("No objects to retrieve given the criteria"); } else { //Get a particular service request (full projection) and update it by adding an action log entry and string strServiceRequestId = null; if (oprServiceRequestsView.Count > 0) { strServiceRequestId = oprServiceRequestsView.ElementAtOrDefault <EnterpriseManagementObjectProjection>(Helper.GetRandomNumber(0, oprServiceRequestsView.Count - 1)).Object[mpcServiceRequest, "Id"].Value.ToString(); } if (strServiceRequestId != null) { string strCriteriaXml = Helper.SearchWorkItemByIDCriteriaXml(strServiceRequestId, mpSystemWorkItemLibrary.Name, mpSystemWorkItemLibrary.Version.ToString(), mpSystemWorkItemLibrary.KeyToken, "System.WorkItem"); ObjectProjectionCriteria opServiceRequestFull = new ObjectProjectionCriteria(strCriteriaXml, mptpServiceRequestFull, emg); IObjectProjectionReader <EnterpriseManagementObject> oprServiceRequestFull = emg.EntityObjects.GetObjectProjectionReader <EnterpriseManagementObject>(opServiceRequestFull, ObjectQueryOptions.Default); EnterpriseManagementObjectProjection emopServiceRequestFull = oprServiceRequestFull.First <EnterpriseManagementObjectProjection>(); if (bSimulateHumanWaitTime) { Thread.Sleep(intDoWorkPause); } emopServiceRequestFull.Object[mpcServiceRequest, "Description"].Value = Guid.NewGuid().ToString(); int intRandomEnumId = Helper.GetRandomNumber(0, listSRAreaEnums.Count); ManagementPackEnumeration mpeArea = listSRAreaEnums.ElementAtOrDefault <ManagementPackEnumeration>(intRandomEnumId); emopServiceRequestFull.Object[mpcServiceRequestExtension, "Area"].Value = mpeArea; emopServiceRequestFull.Overwrite(); DateTime dtServiceRequestWorkEnd = DateTime.Now; TimeSpan tsServiceRequestWork = dtServiceRequestWorkEnd - dtServiceRequestWorkStart; pcServiceRequestWork.RawValue = (long)tsServiceRequestWork.TotalSeconds; Console.WriteLine("Service request work completed (seconds): " + tsServiceRequestWork.TotalSeconds); } } }
public static IObjectProjectionReader <EnterpriseManagementObject> GetBufferedObjectProjectionReader(string strCriteria, int intNumberOfItemsToGet, ManagementPackTypeProjection mptp, EnterpriseManagementGroup emg) { if (intNumberOfItemsToGet > 0) { ObjectProjectionCriteria opc = new ObjectProjectionCriteria(strCriteria, mptp, emg); ObjectQueryOptions oqo = new ObjectQueryOptions(); oqo.ObjectRetrievalMode = ObjectRetrievalOptions.Buffered; oqo.MaxResultCount = intNumberOfItemsToGet; oqo.DefaultPropertyRetrievalBehavior = ObjectPropertyRetrievalBehavior.All; IObjectProjectionReader <EnterpriseManagementObject> reader = emg.EntityObjects.GetObjectProjectionReader <EnterpriseManagementObject>(opc, oqo); return(reader); } else { return(null); } }
private void TestGettingARandomNumberOfIncidents() { EnterpriseManagementGroup emg = new EnterpriseManagementGroup(txtServerName.Text); ManagementPackClass mpcIncident = Helper.GetClassByName("System.WorkItem.Incident", emg); ManagementPack mpIncidentLibrary = mpcIncident.GetManagementPack(); ManagementPackTypeProjection mptpIncidentFull = Helper.GetTypeProjectionByName("System.WorkItem.Incident.ProjectionType", emg); string strCriteria = Helper.SearchWorkItemByLikeIDCriteriaXml("2", mpIncidentLibrary.Name, mpIncidentLibrary.Version.ToString(), mpIncidentLibrary.KeyToken, mpcIncident.Name); IObjectProjectionReader <EnterpriseManagementObject> reader = Helper.GetBufferedObjectProjectionReader(strCriteria, 30, mptpIncidentFull, emg); double dIncidentIDSum = 0; foreach (EnterpriseManagementObjectProjection emop in reader) { string strID = emop.Object[mpcIncident, "Id"].Value.ToString(); dIncidentIDSum += (double)Int32.Parse(strID); } MessageBox.Show(dIncidentIDSum.ToString()); }
private void TestGettingIncidentsByGUIDVsWorkItemID() { EnterpriseManagementGroup emg = new EnterpriseManagementGroup(txtServerName.Text); ManagementPackClass mpcIncident = Helper.GetClassByName("System.WorkItem.Incident", emg); ManagementPack mpIncidentLibrary = mpcIncident.GetManagementPack(); IObjectReader <EnterpriseManagementObject> readerAllIncidents = emg.EntityObjects.GetObjectReader <EnterpriseManagementObject>(mpcIncident, ObjectQueryOptions.Default); ManagementPackTypeProjection mptpIncidentFull = Helper.GetTypeProjectionByName("System.WorkItem.Incident.ProjectionType", emg); double dByGUIDElapsedTime = 0; double dByWorkItemIDElapsedTime = 0; double dNumberOfTries = 1000; double i = 0; do { i++; int intRandomIncident = Helper.GetRandomNumber(0, readerAllIncidents.Count); EnterpriseManagementObject emoIncident = readerAllIncidents.ElementAtOrDefault <EnterpriseManagementObject>(intRandomIncident); Guid guidIncidentId = emoIncident.Id; string strWorkItemID = emoIncident[mpcIncident, "Id"].Value.ToString(); DateTime dtByGUIDStart = DateTime.Now; EnterpriseManagementObjectProjection emopIncident = emg.EntityObjects.GetObjectProjectionWithAccessRights <EnterpriseManagementObject>(emoIncident.Id, mptpIncidentFull); DateTime dtByGUIDEnd = DateTime.Now; TimeSpan tsByGUID = dtByGUIDEnd - dtByGUIDStart; dByGUIDElapsedTime += tsByGUID.Milliseconds; DateTime dtByWorkItemIDStart = DateTime.Now; string strCriteria = Helper.SearchWorkItemByIDCriteriaXml(strWorkItemID, mpIncidentLibrary.Name, mpIncidentLibrary.Version.ToString(), mpIncidentLibrary.KeyToken, mpcIncident.Name); IObjectProjectionReader <EnterpriseManagementObject> readerIncident = Helper.GetBufferedObjectProjectionReader(strCriteria, 1, mptpIncidentFull, emg); DateTime dtByWorkItemIDEnd = DateTime.Now; TimeSpan tsByWorkItemID = dtByWorkItemIDEnd - dtByWorkItemIDStart; dByWorkItemIDElapsedTime += tsByWorkItemID.Milliseconds; pbProgress.Value = (int)(i / dNumberOfTries * 100); }while (i < dNumberOfTries); MessageBox.Show(string.Format("By GUID: {0} By Work Item ID: {1}", dByGUIDElapsedTime.ToString(), dByWorkItemIDElapsedTime.ToString())); }
public override void ExecuteCommand(IList <NavigationModelNodeBase> nodes, NavigationModelNodeTask task, ICollection <string> parameters) { // getting the Management Group Connection that is used by the Console (as it should already be open) ConsoleSdkConnection.IManagementGroupSession session = FrameworkServices.GetService <ConsoleSdkConnection.IManagementGroupSession>(); EnterpriseManagementGroup emg = session.ManagementGroup; // verifying if the MG Connection is closed and reconnecting if needed if (!emg.IsConnected) { emg.Reconnect(); } // getting some types we need and which we are going to use further in our code in the actual processing ManagementPack incidentMp = emg.GetManagementPack(ManagementPacks.incidentLibrary, Constants.mpKeyTocken, Constants.mpSMR2Version); ManagementPack wiLibraryMp = emg.GetManagementPack(ManagementPacks.workItemLibrary, Constants.mpKeyTocken, Constants.mpSMR2Version); ManagementPack incidentSettingsMp = emg.GetManagementPack(ManagementPacks.incidentManagementLibrary, Constants.mpKeyTocken, Constants.mpSMR2Version); ManagementPack activityLibMp = emg.GetManagementPack(ManagementPacks.activityLibrary, Constants.mpKeyTocken, Constants.mpSMR2Version); ManagementPackClass incidentClass = emg.EntityTypes.GetClass(ClassTypes.incident, incidentMp); ManagementPackClass analystCommentClass = emg.EntityTypes.GetClass(ClassTypes.analystCommentLog, wiLibraryMp); ManagementPackEnumerationCriteria incidentClosedEnumCriteria = new ManagementPackEnumerationCriteria(string.Format("Name = '{0}'", EnumTypes.incidentStatusClosed)); ManagementPackEnumeration incidentClosedStatus = emg.EntityTypes.GetEnumerations(incidentClosedEnumCriteria).FirstOrDefault(); ManagementPackTypeProjection incidentProjection = emg.EntityTypes.GetTypeProjection(TypeProjections.incidentAdvanced, incidentSettingsMp); // this is needed in order to know which Activities map to which Activity Profix types // this is the case because each Activity can have a different type, but the Prefix used is saved in the same class-object (System.GlobalSetting.ActivitySettings) IDictionary <string, string> activityPrefixMapping = new Dictionary <string, string> { { ActivityTypes.dependent, ActivityPrefixes.dependent }, { ActivityTypes.manual, ActivityPrefixes.manual }, { ActivityTypes.parallel, ActivityPrefixes.parallel }, { ActivityTypes.review, ActivityPrefixes.review }, { ActivityTypes.sequential, ActivityPrefixes.sequential }, { ActivityTypes.runbook, ActivityPrefixes.runbook } }; // setting up the (string) variables which we are going to use to decide what type of WorkItem we are going to create and different options/aspects of it string workItemClassName = string.Empty; string workItemMpName = string.Empty; string workItemSettingClassName = string.Empty; string workItemSettingPrefixName = string.Empty; string workItemSettingMpName = string.Empty; string workItemTemplateName = string.Empty; string workItemStatusName = string.Empty; string workItemUrgencyName = string.Empty; string workItemImpactName = string.Empty; string workItemCategoryName = string.Empty; // if/elseif code to set the variables that define the differences between what WorkItem type we need to create based on the parameter passed by the Task if (parameters.Contains(TaskActions.Service)) { workItemClassName = ClassTypes.service; workItemMpName = ManagementPacks.serviceLibrary; workItemSettingClassName = WorkItemSettings.service; workItemSettingPrefixName = WorkItemPrefixes.service; workItemSettingMpName = ManagementPacks.serviceManagementLibrary; workItemTemplateName = WorkItemTemplates.service; workItemStatusName = EnumTypes.serviceStatusNew; } else if (parameters.Contains(TaskActions.Change)) { workItemClassName = ClassTypes.change; workItemMpName = ManagementPacks.changeLibrary; workItemSettingClassName = WorkItemSettings.change; workItemSettingPrefixName = WorkItemPrefixes.change; workItemSettingMpName = ManagementPacks.changeManagementLibrary; workItemTemplateName = WorkItemTemplates.change; workItemStatusName = EnumTypes.changeStatusNew; } else if (parameters.Contains(TaskActions.Problem)) { workItemClassName = ClassTypes.problem; workItemMpName = ManagementPacks.problemLibrary; workItemSettingClassName = WorkItemSettings.problem; workItemSettingPrefixName = WorkItemPrefixes.problem; workItemSettingMpName = ManagementPacks.problemLibrary; workItemTemplateName = WorkItemTemplates.problem; workItemStatusName = EnumTypes.problemStatusActive; workItemUrgencyName = EnumTypes.problemUrgencyLow; workItemImpactName = EnumTypes.problemImpactLow; workItemCategoryName = EnumTypes.problemCategoryDefault; } else if (parameters.Contains(TaskActions.Release)) { workItemClassName = ClassTypes.release; workItemMpName = ManagementPacks.releaseLibrary; workItemSettingClassName = WorkItemSettings.release; workItemSettingPrefixName = WorkItemPrefixes.release; workItemSettingMpName = ManagementPacks.releaseManagementLibrary; workItemTemplateName = WorkItemTemplates.release; workItemStatusName = EnumTypes.releaseStatusNew; } // here is the code that does the actual work // we wrap this around a try/catch block to handle any exception that may happen and display it in case of failure try { // getting the types we need based on the string variables we have filled earlier based on the WorkItem type we need to create ManagementPack workItemMp = emg.GetManagementPack(workItemMpName, Constants.mpKeyTocken, Constants.mpSMR2Version); ManagementPack mpSettings = emg.GetManagementPack(workItemSettingMpName, Constants.mpKeyTocken, Constants.mpSMR2Version); ManagementPack knowledgeLibraryMp = emg.GetManagementPack(ManagementPacks.knowledgeLibrary, Constants.mpKeyTocken, Constants.mpSMR2Version); ManagementPackClass workItemClass = emg.EntityTypes.GetClass(workItemClassName, workItemMp); ManagementPackClass workItemClassSetting = emg.EntityTypes.GetClass(workItemSettingClassName, mpSettings); EnterpriseManagementObject generalSetting = emg.EntityObjects.GetObject <EnterpriseManagementObject>(workItemClassSetting.Id, ObjectQueryOptions.Default); // here is the foreach loop that processes each class-object (in this case Incident) that was multi-selected in the view before executing the Task foreach (NavigationModelNodeBase node in nodes) { // we need to setup an IList which contains only 1 GUID that correspons to the Incident we are currently working on (node["Id"]) // this is needed because we are using the IObjectProjectionReader.GetData(...) which gets an IList<Guid> as parameter in order to retreive the class-objects we want from the db IList <Guid> bmeIdsList = new List <Guid>(); bmeIdsList.Add(new Guid(node[Constants.nodePropertyId].ToString())); // we are setting up the ObjectProjectionCriteria using the "System.WorkItem.Incident.ProjectionType" Type Projection as we need to get all the Relationships of the Incident // we will use ObjectRetrievalOptions.Buffered so that we don't get any data from the db which we don't need - we will only get the data one we call the IObjectProjectionReader.GetData(...) method // we are getting the data reader object using GetObjectProjectionReader(...) and setting its PageSize to 1 because we only need 1 object retrieved here ObjectProjectionCriteria incidentObjectProjection = new ObjectProjectionCriteria(incidentProjection); ObjectQueryOptions queryOptions = new ObjectQueryOptions(ObjectPropertyRetrievalBehavior.All); queryOptions.ObjectRetrievalMode = ObjectRetrievalOptions.Buffered; IObjectProjectionReader <EnterpriseManagementObject> incidentReader = emg.EntityObjects.GetObjectProjectionReader <EnterpriseManagementObject>(incidentObjectProjection, queryOptions); incidentReader.PageSize = 1; // we are using EnterpriseManagementObjectProjection for the Incident we are getting from the db instead of EnterpriseManagementObject // this is because we are getting a (Type) Projection object (class-object together with its Relationships & relationship class-objects EnterpriseManagementObjectProjection incident = incidentReader.GetData(bmeIdsList).FirstOrDefault(); // we are doing the same for the new WorkItem class-object we are creating because we want to add Relationships (with their relationship class-objects from the Incident) here as well // if we would only have created the new WorkItem class and nothing else with it (no Relationships), we could have used the CreatableEnterpriseManagementObject class (which needs to be used when a new class-object is getting created) EnterpriseManagementObjectProjection workItem = new EnterpriseManagementObjectProjection(emg, workItemClass); // now we need to assign some Template to the new WorkItem (if a default/standard Template exists) in order to already have some Activities created // the Activities and all other Properties of the new WorkItem can be adjusted by modifying the default/standard Template for each WorkItem type if (!string.IsNullOrEmpty(workItemTemplateName)) { ManagementPackObjectTemplateCriteria templateCriteria = new ManagementPackObjectTemplateCriteria(string.Format("Name = '{0}'", workItemTemplateName)); ManagementPackObjectTemplate template = emg.Templates.GetObjectTemplates(templateCriteria).FirstOrDefault(); if (template != null) { // if a Template with this name exists, we apply it to the new WorkItem by calling ApplyTemplate(...) on it workItem.ApplyTemplate(template); // if we have a Template, we also need to process each Activity that it contains in order to set the Prefix for each Activity (based on its type) // we are using the activityPrefixMapping variable we defined above in oder to map each Prefix based on each Activity class-type ManagementPack activityManagementMp = emg.GetManagementPack(ManagementPacks.activityManagementLibrary, Constants.mpKeyTocken, Constants.mpSMR2Version); ManagementPackRelationship workItemContainsActivityRelationshipClass = emg.EntityTypes.GetRelationshipClass(RelationshipTypes.workItemContainsActivity, activityLibMp); ManagementPackClass activitySettingsClass = emg.EntityTypes.GetClass(ClassTypes.activitySettings, activityManagementMp); EnterpriseManagementObject activitySettings = emg.EntityObjects.GetObject <EnterpriseManagementObject>(activitySettingsClass.Id, ObjectQueryOptions.Default); // for each Activity that exists in the Template we applied, we are going to get its Prefix setting and apply it to its ID in the format: "PREFIX{0}" // "{0}" is the string pattern we need to set for any new WorkItem (including Activity) class-object we are creating as this will be replaced by the next ID available for the new WorkItem foreach (IComposableProjection activity in workItem[workItemContainsActivityRelationshipClass.Target]) { ManagementPackClass activityClass = activity.Object.GetClasses(BaseClassTraversalDepth.None).FirstOrDefault(); string prefix = activitySettings[null, activityPrefixMapping[activityClass.Name]].Value as string; activity.Object[null, ActivityProperties.Id].Value = string.Format("{0}{1}", prefix, Constants.workItemPrefixPattern); } } } // we are setting the Properties for the new WorkItem class-object here from some Properties of the inital Incident (add more as needed) // it is of highest importance that we also set its status to New/Active (depending on WorkItem class-type) in order for it to be properly processed by the internal workflows on creation // if we don't set the the correct "creation" Status here, it will never be able to progress into a working state and will remain stuck in a "pending" state ManagementPackEnumerationCriteria workItemStatusNewEnumCriteria = new ManagementPackEnumerationCriteria(string.Format("Name = '{0}'", workItemStatusName)); ManagementPackEnumeration workItemStatusNew = emg.EntityTypes.GetEnumerations(workItemStatusNewEnumCriteria).FirstOrDefault(); workItem.Object[workItemClass, WorkItemProperties.Id].Value = string.Format("{0}{1}", generalSetting[workItemClassSetting, workItemSettingPrefixName], Constants.workItemPrefixPattern); workItem.Object[workItemClass, WorkItemProperties.Title].Value = string.Format("{0} ({1})", incident.Object[incidentClass, WorkItemProperties.Title].Value, incident.Object[incidentClass, WorkItemProperties.Id].Value); workItem.Object[workItemClass, WorkItemProperties.Description].Value = incident.Object[incidentClass, WorkItemProperties.Description].Value; workItem.Object[workItemClass, WorkItemProperties.Status].Value = workItemStatusNew.Id; // due to the fact that the Problem WorkItem does not have any Template we can use to create it, we need to handle this special case // we need to populate all the required fields when creating the Problem WorkItem, or creating it will fail (Urgency, Impact, Category) if (!string.IsNullOrEmpty(workItemUrgencyName)) { ManagementPackEnumerationCriteria workItemUrgencyEnumCriteria = new ManagementPackEnumerationCriteria(string.Format("Name = '{0}'", workItemUrgencyName)); ManagementPackEnumeration workItemUrgency = emg.EntityTypes.GetEnumerations(workItemUrgencyEnumCriteria).FirstOrDefault(); workItem.Object[workItemClass, WorkItemProperties.Urgency].Value = workItemUrgency.Id; } if (!string.IsNullOrEmpty(workItemImpactName)) { ManagementPackEnumerationCriteria workItemImpactEnumCriteria = new ManagementPackEnumerationCriteria(string.Format("Name = '{0}'", workItemImpactName)); ManagementPackEnumeration workItemImpact = emg.EntityTypes.GetEnumerations(workItemImpactEnumCriteria).FirstOrDefault(); workItem.Object[workItemClass, WorkItemProperties.Impact].Value = workItemImpact.Id; } if (!string.IsNullOrEmpty(workItemCategoryName)) { ManagementPackEnumerationCriteria workItemCategoryEnumCriteria = new ManagementPackEnumerationCriteria(string.Format("Name = '{0}'", workItemCategoryName)); ManagementPackEnumeration workItemCategory = emg.EntityTypes.GetEnumerations(workItemCategoryEnumCriteria).FirstOrDefault(); workItem.Object[workItemClass, WorkItemProperties.Category].Value = workItemCategory.Id; } // we are adding the initial Incident to this new WorkItem as related WorkItem (System.WorkItemRelatesToWorkItem) ManagementPackRelationship workItemToWorkItemRelationshipClass = emg.EntityTypes.GetRelationshipClass(RelationshipTypes.workItemRelatesToWorkItem, wiLibraryMp); workItem.Add(incident.Object, workItemToWorkItemRelationshipClass.Target); // we are closing the current Incident by setting its Status to Closed and setting a closed date incident.Object[incidentClass, IncidentProperties.Status].Value = incidentClosedStatus.Id; incident.Object[incidentClass, IncidentProperties.ClosedDate].Value = DateTime.Now.ToUniversalTime(); // we create a new (analyst) comment (System.WorkItem.TroubleTicket.AnalystCommentLog) and we add it to the Incident in oder to comment the fact that it was closed tue to this WorkItem Transfomr Task CreatableEnterpriseManagementObject analystComment = new CreatableEnterpriseManagementObject(emg, analystCommentClass); analystComment[analystCommentClass, AnalystCommentProperties.Id].Value = Guid.NewGuid().ToString(); analystComment[analystCommentClass, AnalystCommentProperties.Comment].Value = string.Format(Constants.incidentClosedComment, workItemClass.Name, workItem.Object.Id.ToString()); analystComment[analystCommentClass, AnalystCommentProperties.EnteredBy].Value = EnterpriseManagementGroup.CurrentUserName; analystComment[analystCommentClass, AnalystCommentProperties.EnteredDate].Value = DateTime.Now.ToUniversalTime(); ManagementPackRelationship incidentHasAnalystCommentRelationshipClass = emg.EntityTypes.GetRelationshipClass(RelationshipTypes.workItemHasAnalystComment, wiLibraryMp); incident.Add(analystComment, incidentHasAnalystCommentRelationshipClass.Target); // we create an IList of RelationshipTypes we want to transfer from the Incident to the new WorkItem // this is the place we can add any new/custom RelationshipTypes which we want to transfer // just make sure that the RelationshipType can be transfered from an Incident to any other WorkItem class-type IList <ManagementPackRelationship> relationshipsToAddList = new List <ManagementPackRelationship>() { workItemToWorkItemRelationshipClass, emg.EntityTypes.GetRelationshipClass(RelationshipTypes.createdByUser, wiLibraryMp), emg.EntityTypes.GetRelationshipClass(RelationshipTypes.affectedUser, wiLibraryMp), emg.EntityTypes.GetRelationshipClass(RelationshipTypes.assignedToUser, wiLibraryMp), emg.EntityTypes.GetRelationshipClass(RelationshipTypes.workItemHasAttachment, wiLibraryMp), emg.EntityTypes.GetRelationshipClass(RelationshipTypes.workItemAboutConfigItem, wiLibraryMp), emg.EntityTypes.GetRelationshipClass(RelationshipTypes.workItemRelatesToConfigItem, wiLibraryMp), emg.EntityTypes.GetRelationshipClass(RelationshipTypes.entityToArticle, knowledgeLibraryMp), emg.EntityTypes.GetRelationshipClass(RelationshipTypes.workItemHasCommentLog, wiLibraryMp), }; // we are getting an instance of the "System.Membership" RelationshipType as we need to handle RelationshipTypes derived from it as a special case // the reason for this, is that Target class-objects of the "System.Membership" RelationshipType are bound to their Source class-objects // being bound, means that Target class-objects of membership relationships cannot belong to 2 different (Source) class-objects // because of this, we need to make a copy (using "CreatableEnterpriseManagementObject" to create a new object and copying the Properties) of the existing Target class-object // and add that to the new WorkItem instead of adding the already existing Target class-object ManagementPack systemLibraryMp = emg.GetManagementPack(ManagementPacks.systemLibrary, Constants.mpKeyTocken, Constants.mpSMR2Version); ManagementPackRelationship membershipRelationshipClass = emg.EntityTypes.GetRelationshipClass(RelationshipTypes.membership, systemLibraryMp); // we are going through each Target & Source Relationships of the Incident as defined in the relationshipsToAddList variable and adding them to the new WorkItem // we are handling the Target RelationshipTypes which are derived from "System.Membership" as a special case as explained above // notice that we are also removing these Relationships from the Incident by calling Remove() // we are removing the Relationships from the Incident for performance purposes - in order to have less Relationships (less data) in the db // comment the "itemProjection.Remove();" in order to keep the Relationships to the Incident as well if needed for some reason foreach (ManagementPackRelationship relationship in relationshipsToAddList) { if (incident[relationship.Target].Any()) { foreach (IComposableProjection itemProjection in incident[relationship.Target]) { // create a new Target class-object (CreatableEnterpriseManagementObject) and add it to the projection as it is a member of a Membership RelationshipType (as explained above) // notice that we DON'T remove such a Target class-object Relationship because it will also remove the class-object itself (because it is a Membership RelationshipType object and it cannot exist without this Relationship) // we need it to exist because we are copying data from it and it needs to still exist in the db (ex. Attachments - we still need the binary data to exist in the db when we create the new Attachment object) // we could of course delete it after we create the new WorkItem with its Relationships when calling "workItem.Overwrite()", but I chose not to do it if (relationship.IsSubtypeOf(membershipRelationshipClass)) { CreatableEnterpriseManagementObject instance = new CreatableEnterpriseManagementObject(emg, itemProjection.Object.GetClasses(BaseClassTraversalDepth.None).FirstOrDefault()); foreach (ManagementPackProperty property in itemProjection.Object.GetProperties()) { instance[property.Id].Value = itemProjection.Object[property.Id].Value; } instance[null, Constants.entityId].Value = Guid.NewGuid().ToString(); workItem.Add(instance, relationship.Target); } // just add the existing Target object-class as it is not a member of a Membership RelationshipType (as explained above) else { workItem.Add(itemProjection.Object, relationship.Target); itemProjection.Remove(); } } } if (incident[relationship.Source].Any()) { // we just create the new Relationship of the Source class-object to the new WorkItem because this is not affected by the Membership RelationshipType foreach (IComposableProjection itemProjection in incident[relationship.Source]) { workItem.Add(itemProjection.Object, relationship.Source); itemProjection.Remove(); } } } // this is where we actually save (write) the new data to the db, when calling "Overwrite()" - here saving the Incident we modified (set Status to Closed & deleted Relationships) // before we have just created the new objects and relationships in-memory // this is also the point when almost all of the code validation is being done // if there are any issues really creating/editing/adding these objects/realtionships, this is where we would get the errors incident.Overwrite(); // we are want to handle the error here of saving the new WorkItem and its Relationships because we want to re-open the Incident in case there is an issue when creating the new WorkItem try { // this is where we actually save (write) the new data to the db, when calling "Overwrite()" - here saving the new WorkItem we created with its Relationships we added (from the Incident) workItem.Overwrite(); } catch (Exception ex) { // if we faild to create the new WorkItem with its Relationships, we want to revert to setting the Incident to an Active Status (we re-open the Incident) ManagementPackEnumerationCriteria incidentActiveEnumCriteria = new ManagementPackEnumerationCriteria(string.Format("Name = '{0}'", EnumTypes.incidentStatusActive)); ManagementPackEnumeration incidentActiveStatus = emg.EntityTypes.GetEnumerations(incidentActiveEnumCriteria).FirstOrDefault(); incident.Object[incidentClass, IncidentProperties.Status].Value = incidentActiveStatus.Id; incident.Object[incidentClass, IncidentProperties.ClosedDate].Value = null; // again, after applying the new modifications in memory, we need to actually write them to the db using "Overwrite()" incident.Overwrite(); // no need to show this because we are just passing it (throwing) to the wrapped try/catch block so it will be displayed and handled there throw ex; } } // if everything succeeds, we want to refresh the View (in this case, some View that shows Incidents as this is where we are calling our Task from) // we want to refresh the view to show the new Status of the Incient (as Closed in this case) - if the View only shows non-Closed Incidents, it will dissapear from the View RequestViewRefresh(); } catch (Exception ex) { // we want to handle all Exceptions here so that the Console does not crash // we also want to show a MessageBox window with the Exception details for troubleshooting purposes MessageBox.Show(string.Format("Error: {0}: {1}\n\n{2}", ex.GetType().ToString(), ex.Message, ex.StackTrace)); } }
public String Copy() { string strWorkItemID = null; #region MPVariables ManagementPack mpIncidentLibrary = Common.GetManagementPackByName(Constants.strManagementPackIncidentLibrary, this.EMG); ManagementPackTypeProjection mptpIncident = Common.GetManagementPackTypeProjectionByName(Constants.strTypeProjectionIncident, Constants.strManagementPackIncidentManagementLibrary, this.EMG); ManagementPackClass mpcIncident = Common.GetManagementPackClassByName(Constants.strClassIncident, Constants.strManagementPackIncidentLibrary, this.EMG); ManagementPackRelationship mprCreatedByUser = Common.GetManagementPackRelationshipByName(Constants.strRelationshipCreatedByUser, Constants.strManagementPackWorkItemLibrary, this.EMG); ManagementPackEnumeration mpeIncidentStatusActive = Common.GetManagementPackEnummerationByName(Constants.strEnumerationIncidentStatusActive, Constants.strManagementPackIncidentLibrary, this.EMG); ManagementPackRelationship mprWorkItemRelatesToWorkItem = Common.GetManagementPackRelationshipByName(Constants.strRelationshipWorkItemRelatesToWorkItem, Constants.strManagementPackWorkItemLibrary, this.EMG); #endregion string strIncidentIDPrefix = GetIncidentIDPrefix(); //Create the criteria to get the object by the Work Item ID passed in String strIncidentByIDCriteria = String.Format(@"<Criteria xmlns=""http://Microsoft.EnterpriseManagement.Core.Criteria/"">" + "<Expression>" + "<SimpleExpression>" + "<ValueExpressionLeft>" + "<Property>$Target/Property[Type='System.WorkItem.Incident']/Id$</Property>" + "</ValueExpressionLeft>" + "<Operator>Equal</Operator>" + "<ValueExpressionRight>" + "<Value>{0}</Value>" + "</ValueExpressionRight>" + "</SimpleExpression>" + "</Expression>" + "</Criteria>", this.IDToCopy); ObjectProjectionCriteria opcIncidentByID = new ObjectProjectionCriteria(strIncidentByIDCriteria, mptpIncident, mpIncidentLibrary, this.EMG); //Get the incident type projection by ID IObjectProjectionReader <EnterpriseManagementObject> emopIncidents = this.EMG.EntityObjects.GetObjectProjectionReader <EnterpriseManagementObject>(opcIncidentByID, ObjectQueryOptions.Default); foreach (EnterpriseManagementObjectProjection emopIncident in emopIncidents) { //Note: We are using foreach here but there will be only one since we are searching by the work item ID if (this.PropertiesToExclude.Length == 0) { //A list of Properties to exclude was not passed in so we are going to go with a default list. this.PropertiesToExclude = new string[] { Constants.strPropertyId, Constants.strPropertyCreatedDate, Constants.strPropertyStatus, Constants.strPropertyTargetResolutionTime, Constants.strPropertyResolutionCategory, Constants.strPropertyResolutionDescription, Constants.strPropertyClosedDate, Constants.strPropertyDisplayName }; } //Copy all the properties (including extended properties, except for those specified EnterpriseManagementObjectProjection emopNewIncident = Common.CreateNewObjectProjectionFromExistingObjectProjection(emopIncident, mpcIncident, this.PropertiesToExclude, this.EMG); //Set the ID, DisplayName, Status, and CreatedDate properties emopNewIncident.Object[mpcIncident, Constants.strPropertyStatus].Value = mpeIncidentStatusActive; emopNewIncident.Object[mpcIncident, Constants.strPropertyId].Value = String.Format("{0}{1}", strIncidentIDPrefix, "{0}"); emopNewIncident.Object[mpcIncident, Constants.strPropertyCreatedDate].Value = DateTime.Now.ToUniversalTime(); emopNewIncident.Object[mpcIncident, Constants.strPropertyDisplayName].Value = String.Format("{0} - {1}", emopNewIncident.Object[mpcIncident, Constants.strPropertyId].Value, emopNewIncident.Object[mpcIncident, Constants.strPropertyTitle].Value); if (this.RelationshipAliasesToExclude.Length == 0) { //A list of Relationships to exclude was not passed in so we are going to go with a default list. this.RelationshipAliasesToExclude = new string[] { Constants.strAliasCreatedByUser, Constants.strAliasClosedByUser, Constants.strAliasResolvedByUser, Constants.strAliasActionLogs, Constants.strAliasUserComments, Constants.strAliasAnalystComments, Constants.strAliasSMTPNotifications, Constants.strAliasActivities, Constants.strAliasFileAttachments }; } //Copy all the relationships defined in the type projection, except for those specified Common.CopyRelationships(emopIncident, ref emopNewIncident, mptpIncident, this.RelationshipAliasesToExclude); //Set CreatedByUser to be the user that is logged in EnterpriseManagementObject emoCreatedByUser = Common.GetLoggedInUserAsObject(this.EMG); if (emoCreatedByUser != null) { emopNewIncident.Add(emoCreatedByUser, mprCreatedByUser.Target); } //Relate the original incident to the new one emopNewIncident.Add(emopIncident.Object, mprWorkItemRelatesToWorkItem.Target); //And finally submit... emopNewIncident.Commit(); strWorkItemID = emopNewIncident.Object[mpcIncident, Constants.strPropertyId].Value.ToString(); } return(strWorkItemID); }
private static void DoSomeChangeRequestWork() { DateTime dtChangeRequestWorkStart = DateTime.Now; //Query and get some change requests using just the view type projection int intRandomAreaEnum = Helper.GetRandomNumber(0, listCRAreaEnums.Count); ManagementPackEnumeration mpeRandomArea = listCRAreaEnums.ElementAtOrDefault <ManagementPackEnumeration>(intRandomAreaEnum); string strCriteria = Helper.SearchObjectByEnumerationCriteriaXml(mpeRandomArea, mpcChangeRequest, mppChangeRequestArea); IObjectProjectionReader <EnterpriseManagementObject> oprChangeRequestView = Helper.GetBufferedObjectProjectionReader(strCriteria, intNumberOfWorkItemsToGet, mptpChangeRequestView, emg); if (oprChangeRequestView == null) { Console.WriteLine("No objects to retrieve given the criteria"); } else { //Get a particular incident (full projection) and update it by adding an action log entry and string strChangeRequestId = null; if (oprChangeRequestView.Count > 0) { strChangeRequestId = oprChangeRequestView.ElementAtOrDefault <EnterpriseManagementObjectProjection>(Helper.GetRandomNumber(0, oprChangeRequestView.Count - 1)).Object[mpcChangeRequest, "Id"].Value.ToString(); } if (strChangeRequestId != null) { //Get the change request to update string strCriteriaXml = Helper.SearchWorkItemByIDCriteriaXml(strChangeRequestId, mpSystemWorkItemLibrary.Name, mpSystemWorkItemLibrary.Version.ToString(), mpSystemWorkItemLibrary.KeyToken, "System.WorkItem"); ObjectProjectionCriteria opcChangeRequestFull = new ObjectProjectionCriteria(strCriteriaXml, mptpChangeRequestFull, emg); IObjectProjectionReader <EnterpriseManagementObject> oprChangeRequestFull = emg.EntityObjects.GetObjectProjectionReader <EnterpriseManagementObject>(opcChangeRequestFull, ObjectQueryOptions.Default); EnterpriseManagementObjectProjection emopChangeRequestFull = oprChangeRequestFull.First <EnterpriseManagementObjectProjection>(); if (bSimulateHumanWaitTime) { Thread.Sleep(intDoWorkPause); } //Update a couple of properties on the change request emopChangeRequestFull.Object[mpcChangeRequest, "Description"].Value = Guid.NewGuid().ToString(); int intRandomEnumID = Helper.GetRandomNumber(0, listCRAreaEnums.Count); ManagementPackEnumeration mpeArea = listCRAreaEnums.ElementAtOrDefault <ManagementPackEnumeration>(intRandomEnumID); emopChangeRequestFull.Object[mpcChangeRequestExtension, "Area"].Value = mpeArea; //Add the current user as an affected CI emopChangeRequestFull.Add(emoUser, mprAffectedCI.Target); if (bSimulateHumanWaitTime) { Thread.Sleep(intDoWorkPause); } //Commit the changes to the DB emopChangeRequestFull.Overwrite(); foreach (IComposableProjection icpRelatedCI in emopChangeRequestFull[mprRelatedCI.Target]) { icpRelatedCI.Remove(); } emopChangeRequestFull.Overwrite(); DateTime dtChangeRequestWorkEnd = DateTime.Now; TimeSpan tsChangeRequestWork = dtChangeRequestWorkEnd - dtChangeRequestWorkStart; pcChangeRequestWork.RawValue = (long)tsChangeRequestWork.TotalSeconds; Console.WriteLine("Change request work completed (seconds): " + tsChangeRequestWork.TotalSeconds); } } }
private static void DoSomeIncidentWork() { DateTime dtIncidentWorkStart = DateTime.Now; //Query and get some incidents using just the view type projection int intRandomClassificationEnum = Helper.GetRandomNumber(0, listIncidentClassificationEnums.Count); ManagementPackEnumeration mpeRandomClassification = listIncidentClassificationEnums.ElementAtOrDefault <ManagementPackEnumeration>(intRandomClassificationEnum); string strClassificationCriteriaXml = Helper.SearchObjectByEnumerationCriteriaXml(mpeRandomClassification, mpcIncident, mppIncidentClassification); DateTime dtIncidentQueryStart = DateTime.Now; IObjectProjectionReader <EnterpriseManagementObject> readerIncidentView = Helper.GetBufferedObjectProjectionReader(strClassificationCriteriaXml, intNumberOfWorkItemsToGet, mptpIncidentView, emg); DateTime dtIncidentQueryFinish = DateTime.Now; TimeSpan tsIncidentQueryTime = dtIncidentQueryFinish - dtIncidentQueryStart; pcIncidentQuery.RawValue = (long)tsIncidentQueryTime.TotalSeconds; if (readerIncidentView == null) { Console.WriteLine("No objects to retrieve given the criteria"); } else { Console.WriteLine(String.Format("{0} {1} in {2} seconds.", readerIncidentView.Count.ToString(), mpeRandomClassification.DisplayName, tsIncidentQueryTime.TotalSeconds)); //Get a particular incident (full projection) and update it by adding an action log entry and string strIncidentId = null; if (readerIncidentView.Count > 0) { strIncidentId = readerIncidentView.ElementAtOrDefault <EnterpriseManagementObjectProjection>(Helper.GetRandomNumber(0, readerIncidentView.Count - 1)).Object[mpcIncident, "Id"].Value.ToString(); } if (strIncidentId != null) { DateTime dtGetIncidentStart = DateTime.Now; //Get the incident to update string strCriteriaXml = Helper.SearchWorkItemByIDCriteriaXml(strIncidentId, mpSystemWorkItemLibrary.Name, mpSystemWorkItemLibrary.Version.ToString(), mpSystemWorkItemLibrary.KeyToken, "System.WorkItem"); ObjectProjectionCriteria opcIncidentFull = new ObjectProjectionCriteria(strCriteriaXml, mptpIncidentFull, emg); IObjectProjectionReader <EnterpriseManagementObject> oprIncidentFull = emg.EntityObjects.GetObjectProjectionReader <EnterpriseManagementObject>(opcIncidentFull, ObjectQueryOptions.Default); EnterpriseManagementObjectProjection emopIncidentFull = oprIncidentFull.First <EnterpriseManagementObjectProjection>(); DateTime dtGetIncidentEnd = DateTime.Now; TimeSpan tsGetIncident = dtGetIncidentEnd - dtGetIncidentStart; pcGetSingleIncident.RawValue = (long)tsGetIncident.TotalSeconds; Console.WriteLine("Get single incident time: " + tsGetIncident.TotalSeconds); if (bSimulateHumanWaitTime) { Thread.Sleep(intDoWorkPause); } //Update a couple of properties on the incident emopIncidentFull.Object[mpcIncident, "Description"].Value = Guid.NewGuid().ToString(); int intRandomEnumID = Helper.GetRandomNumber(0, listIncidentClassificationEnums.Count); ManagementPackEnumeration mpeClassification = listIncidentClassificationEnums.ElementAtOrDefault <ManagementPackEnumeration>(intRandomEnumID); emopIncidentFull.Object[mpcIncident, "Classification"].Value = mpeClassification; //Create a new action log entry and add it to the incident CreatableEnterpriseManagementObject cemoAnalystComment = new CreatableEnterpriseManagementObject(emg, mpcAnalystComment); cemoAnalystComment[mpcAnalystComment, "Id"].Value = System.Guid.NewGuid().ToString(); cemoAnalystComment[mpcAnalystComment, "Comment"].Value = System.Guid.NewGuid().ToString(); cemoAnalystComment[mpcAnalystComment, "EnteredBy"].Value = strUserName; cemoAnalystComment[mpcAnalystComment, "EnteredDate"].Value = DateTime.UtcNow; //If it is getting to be more than about 8 comments it is getting unrealistic. Don't keep adding to it. if (emopIncidentFull[mprAnalystComment.Target].Count < 8) { emopIncidentFull.Add(cemoAnalystComment, mprAnalystComment.Target); } //Change the assigned to user to the current user foreach (IComposableProjection icpAssignedToUser in emopIncidentFull[mprWorkItemAssignedToUser.Target]) { icpAssignedToUser.Remove(); } emopIncidentFull.Add(emoUser, mprWorkItemAssignedToUser.Target); if (bSimulateHumanWaitTime) { Thread.Sleep(intDoWorkPause); } //Commit the changes to the DB DateTime dtUpdateIncidentStart = DateTime.Now; emopIncidentFull.Overwrite(); DateTime dtUpdateIncidentEnd = DateTime.Now; TimeSpan tsUpdateIncident = dtUpdateIncidentEnd - dtUpdateIncidentStart; pcUpdateIncident.RawValue = (long)tsUpdateIncident.TotalSeconds; DateTime dtIncidentWorkEnd = DateTime.Now; TimeSpan tsIncidentWork = dtIncidentWorkEnd - dtIncidentWorkStart; pcIncidentWork.RawValue = (long)tsIncidentWork.TotalSeconds; Console.WriteLine("Incident work completed (seconds): " + tsIncidentWork.TotalSeconds); } } }