bool HasDuplicateRecord( OAdEntity hostRecord, string childRecordEntityTypeName, string childRecordDisplayName) { // check if hostRecord already has a duplicate of this childRecord if (!CQWrapper.HasDuplicates(hostRecord)) { return(false); } object[] dupRecObjs = CQWrapper.GetDuplicates(hostRecord) as object[]; foreach (object dupRecObj in dupRecObjs) { OAdLink aLink = dupRecObj as OAdLink; if (null != aLink) { OAdEntity record = CQWrapper.GetChildEntity(aLink) as OAdEntity; if (null != record) { string recDispName = CQWrapper.GetEntityDisplayName(record); string recEntityDefName = CQWrapper.GetEntityDefName(record); if (CQStringComparer.EntityName.Equals(recEntityDefName, childRecordEntityTypeName) && CQStringComparer.RecordName.Equals(recDispName, childRecordDisplayName)) { return(true); } } } } return(false); }
/// <summary> /// Parametrized Constructor for instantiating schema object /// No other CTors are provided as these values are required to start with /// </summary> /// <param name="xmlFile">Name of the target schema xml file</param> /// <param name="cqSess">Handle to valid CQ session</param> /// <param name="entityDef">Handle to valid CQ Entity Definition</param> public WITDXMLGenerator(string schemaXmlFile, string fieldMapXmlFile, Session cqSess, OAdEntityDef entityDef, VSTSConnection vstsConn) { Logger.EnteredMethod(LogSource.CQ, schemaXmlFile, fieldMapXmlFile, cqSess, entityDef); // create instance of WITDFieldMap to store field mappings witdFieldMap = new WITFieldMappings(); // create instance of WITDSchema to store WITD schema witdSchema = new WITDSchema(); witdSchema.SetApplication(Application.Workitemtypeeditor); // set the VSTS connection handle for finding the unique fields in VSTS system WITDSchema.VstsConn = vstsConn; // store file name to be used later to generate xml schemaXMLFileName = schemaXmlFile; fieldMapXMLFileName = fieldMapXmlFile; cqEntityDef = entityDef; cqSession = cqSess; cqEntity = CQWrapper.BuildEntity(cqSession, CQWrapper.GetEntityDefName(cqEntityDef)); Logger.ExitingMethod(LogSource.CQ); }
private void EditRecord(IMigrationAction action, ConversionResult convRslt) { string ownerRecordDisplayName = FindTargetWorkItemId(action); string ownerRecordType = UtilityMethods.ExtractRecordType(action); string changeAuthor = UtilityMethods.ExtractAuthor(action); // find the entity OAdEntity entity = CQWrapper.GetEntity(m_userSession, ownerRecordType, ownerRecordDisplayName); XmlNodeList columns = action.MigrationActionDescription.SelectNodes("/WorkItemChanges/Columns/Column"); if (null == columns) { throw new MigrationException(ClearQuestResource.ClearQuest_Error_InvalidActionDescription, action.ActionId); } string stateField = m_migrationContext.GetStateField(ownerRecordType); XmlNode stateTransitFieldNode = UtilityMethods.ExtractSingleFieldNodeFromMigrationDescription( action.MigrationActionDescription, stateField); bool containsStateTransit = (stateTransitFieldNode != null); if (containsStateTransit) { // change contains state transition List <string> skipFields; if (ChangeRecordState(entity, action, convRslt, stateTransitFieldNode, out skipFields)) { ModifyRecordContent(entity, action, convRslt, skipFields); } } else { ModifyRecordContent(entity, action, convRslt, null); } }
/// <summary> /// Download the XML document describing this CQ record /// </summary> /// <remarks> /// EntityDisplayName, EntityDefName and CQSession properties are needed to retrieve record details /// </remarks> /// <param name="localPath"></param> public void Download(string localPath) { if (null == CQSession) { throw new InvalidOperationException("CQSession == NULL"); } if (File.Exists(localPath)) { File.Delete(localPath); } if (IsRecordHistory) { // download the record history OAdEntity record = CQWrapper.GetEntity(CQSession, EntityDefName, EntityDispName); XmlDocument recordHistDesc = CreateRecordHistoryDesc(record, HistoryValue, HistoryFieldName + "::" + Version, false); recordHistDesc.Save(localPath); } else { // download the *complete* record content (field + value) OAdEntity record = CQWrapper.GetEntity(CQSession, EntityDefName, EntityDispName); XmlDocument recordDesc = CreateRecordDesc(record, Version, null, false); recordDesc.Save(localPath); } }
public ClearQuestAttachmentItem( OAdEntity aHostRecord, OAdAttachmentField aHostField, OAdAttachment aAttachment, ClearQuestConnectionConfig connectionConfiguration) { // gather info to query for the record EntityDefName = CQWrapper.GetEntityDefName(aHostRecord); EntityDispName = CQWrapper.GetEntityDisplayName(aHostRecord); // gather info to query for attachment field FieldName = CQWrapper.GetAttachmentFieldName(aHostField); string name; string comment; string dispName; int fileSize; CQWrapper.GetAttachmentMetadata(aAttachment, out name, out comment, out dispName, out fileSize); Name = name; Comment = comment; DisplayName = dispName; Length = (long)fileSize; // fileSize returned by CQ API is in bytes ConnectionConfiguration = connectionConfiguration; }
public void UpdateAttachment(int workItemId, WITAttachmentChangeAction action) { // find the entity OAdEntity entity = GetEntityByDBId(workItemId); // mark entity to be editable CQWrapper.EditEntity(m_session, entity, "Modify"); foreach (WITAttachment attachment in action.Attachments) { if (attachment.ActionType == AttachmentChangeActionType.Add) { AddAttachment(entity, attachment.FileName, attachment.Comment); } else if (attachment.ActionType == AttachmentChangeActionType.Delete) { throw new NotImplementedException("DeleteAttachment is not supported yet"); } // Update attachment comment else if (attachment.ActionType == AttachmentChangeActionType.Edit) { throw new NotImplementedException("EditAttachment is not supported yet"); } } SaveWorkItem(entity); }
public void ExtractLinkChangeActions( Session session, OAdEntity hostRecord, List <LinkChangeGroup> linkChangeGroups) { string hostRecDispName = CQWrapper.GetEntityDisplayName(hostRecord); string hostRecEntityDefName = CQWrapper.GetEntityDefName(hostRecord); string hostRecMigrItemId = UtilityMethods.CreateCQRecordMigrationItemId(hostRecEntityDefName, hostRecDispName); var linkChangeGroup = new LinkChangeGroup(hostRecMigrItemId, LinkChangeGroup.LinkChangeGroupStatus.Created, false); if (!CQWrapper.HasDuplicates(hostRecord)) { return; } object[] dupRecObjs = CQWrapper.GetDuplicates(hostRecord) as object[]; foreach (object dupRecObj in dupRecObjs) { OAdLink aLink = dupRecObj as OAdLink; if (null != aLink) { OAdEntity childRecord = CQWrapper.GetChildEntity(aLink) as OAdEntity; if (null != childRecord) { string childRecDispName = CQWrapper.GetEntityDisplayName(childRecord); string childRecEntityDefName = CQWrapper.GetEntityDefName(childRecord); string childRecMigrItemId = UtilityMethods.CreateCQRecordMigrationItemId(childRecEntityDefName, childRecDispName); ILink dupLink = new ArtifactLink(hostRecDispName, new Artifact(hostRecMigrItemId, new ClearQuestRecordArtifactType()), new Artifact(childRecMigrItemId, new ClearQuestRecordArtifactType()), string.Empty, this); LinkChangeAction action = new LinkChangeAction(WellKnownChangeActionId.Add, dupLink, LinkChangeAction.LinkChangeActionStatus.Created, false); linkChangeGroup.AddChangeAction(action); } else { // [teyang] TODO replace debug assertion with a conflict? Debug.Assert(false, "null == childRecord"); } } else { // [teyang] TODO replace debug assertion with a conflict? Debug.Assert(false, "null == aLink"); } } linkChangeGroups.Add(linkChangeGroup); }
public ClearQuestRecordItem(OAdEntity aRecord, string version) { Initialize(CQWrapper.GetEntityDefName(aRecord), CQWrapper.GetEntityDisplayName(aRecord), string.Empty, false); Version = version; }
private void SetRecordEditable(OAdEntity cqEntity) { string entityDefName = CQWrapper.GetEntityDefName(cqEntity); OAdEntityDef entityDef = CQWrapper.GetEntityDef(m_userSession, entityDefName); string modifyActionDefName = FindCQActionDefName(entityDef, CQConstants.ACTION_MODIFY); // open the record with the modify action CQWrapper.EditEntity(m_userSession, cqEntity, modifyActionDefName); }
public ChangeSummary GetSummaryOfChangesSince(string lastProcessedChangeItemId, List <string> filterStrings) { // lastProcessedChangeItemId is in a form such as "Defect:UCM0100019437:history:0" // Parse it and query for the record with that Id to get the time is was last changed string[] identity = UtilityMethods.ParseCQRecordMigrationItemId(lastProcessedChangeItemId); OAdEntity lastProcessedRecord = CQWrapper.GetEntity(m_userSession, identity[0], identity[1]); string lastProcessedRecordAuthor; DateTime lastProcessedRecordChangeDate; ClearQuestRecordItem.FindLastRevDtls(lastProcessedRecord, out lastProcessedRecordAuthor, out lastProcessedRecordChangeDate); string lastProcessedRecordChangeDateStr = lastProcessedRecordChangeDate.ToString("u").Replace("Z", ""); // using "ISO 8601" DateTime string format if (lastProcessedRecordChangeDateStr.LastIndexOf('.') >= 0) { lastProcessedRecordChangeDateStr = lastProcessedRecordChangeDateStr.Substring(0, lastProcessedRecordChangeDateStr.LastIndexOf('.')); // drop the millisec } ChangeSummary changeSummary = new ChangeSummary(); changeSummary.ChangeCount = 0; changeSummary.FirstChangeModifiedTimeUtc = DateTime.MinValue; foreach (CQRecordFilter filter in m_filters) { CQRecordQueryBase recordQuery = CQRecordQueryFactory.CreatQuery(m_userSession, filter, lastProcessedRecordChangeDateStr, this); foreach (OAdEntity record in recordQuery) { // HACK HACK if (record != null) // this if check is HACK { DateTime lastChangeDate; string lastAuthor; ClearQuestRecordItem.FindLastRevDtls(record, out lastAuthor, out lastChangeDate); // Make sure the lastChangeDate on this record is after the lastProcessedRecordChangeDate before counting it in the backclog // because the query issued above is imprecise because the milliseconds are dropped if (lastChangeDate > lastProcessedRecordChangeDate) { changeSummary.ChangeCount++; DateTime lastChangeDateUtc = lastChangeDate.ToUniversalTime(); if (changeSummary.FirstChangeModifiedTimeUtc == DateTime.MinValue || lastChangeDateUtc < changeSummary.FirstChangeModifiedTimeUtc) { changeSummary.FirstChangeModifiedTimeUtc = lastChangeDateUtc; } } } } } return(changeSummary); }
internal static void Revert(OAdEntity cqEntity) { try { cqEntity.Revert(); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } }
private void SaveWorkItem(OAdEntity entity) { string retVal = CQWrapper.Validate(entity); Trace.WriteIf(!string.IsNullOrEmpty(retVal), "retVal = " + retVal); Assert.IsTrue(string.IsNullOrEmpty(retVal), "retVal is not empty after validate"); retVal = CQWrapper.Commmit(entity); Trace.WriteIf(!string.IsNullOrEmpty(retVal), "retVal = " + retVal); Assert.IsTrue(string.IsNullOrEmpty(retVal), "retVal is not empty after commit"); }
internal static void EditEntity(Session cqSession, OAdEntity cqEntity, string actionName) { try { cqSession.EditEntity(cqEntity, actionName); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } }
internal ChangeGroup CreateChangeGroup( ChangeGroupService changeGroupService, ClearQuestMigrationContext migrationContext, bool isLastRevOfThisSyncCycle) { ChangeGroup changeGroup = changeGroupService.CreateChangeGroupForDeltaTable(ChangeGroupName); OAdEntity record = CQWrapper.GetEntity(CQSession, EntityDefName, EntityDispName); if (IsRecordHistory) { XmlDocument recordHistDesc = CreateRecordHistoryDesc(record, HistoryValue, HistoryFieldName + "::" + Version, isLastRevOfThisSyncCycle); changeGroup.CreateAction(WellKnownChangeActionId.Edit, this, MigrationRecordId, "", Version, "", WellKnownContentType.WorkItem.ReferenceName, recordHistDesc); } else { XmlDocument recordDesc = CreateRecordDesc(record, Version, migrationContext, isLastRevOfThisSyncCycle); if (Version.Equals(NewRecordVersion, StringComparison.InvariantCulture)) { changeGroup.CreateAction(WellKnownChangeActionId.Add, this, MigrationRecordId, "", Version, "", WellKnownContentType.WorkItem.ReferenceName, recordDesc); } else { changeGroup.CreateAction(WellKnownChangeActionId.Edit, this, MigrationRecordId, "", Version, "", WellKnownContentType.WorkItem.ReferenceName, recordDesc); } } return(changeGroup); }
private bool SetMandatoryFields(IMigrationAction action, ref OAdEntity newRecord, out List <string> processedFields) { XmlNodeList columns = action.MigrationActionDescription.SelectNodes("/WorkItemChanges/Columns/Column"); if (null == columns) { throw new MigrationException(ClearQuestResource.ClearQuest_Error_InvalidActionDescription, action.ActionId); } StringBuilder updateLog = new StringBuilder(); PrintUpdateLogHeader(action, updateLog); processedFields = new List <string>(); foreach (XmlNode columnData in columns) { string stringVal = columnData.FirstChild.InnerText; string fieldName = columnData.Attributes["ReferenceName"].Value; Debug.Assert(!string.IsNullOrEmpty(fieldName), "Field ReferenceName is absent in the Migration Description"); OAdFieldInfo aFieldInfo = CQWrapper.GetEntityFieldValue(newRecord, fieldName); int fieldRequiredness = CQWrapper.GetRequiredness(aFieldInfo); if (fieldRequiredness != CQConstants.MANDATORY) { // skipping all non-mandatory fields continue; } string originalFieldValue = CQWrapper.GetFieldValue(aFieldInfo); int attempt1Count = 0; if (!SetFieldValue(action, newRecord, fieldName, stringVal, ref attempt1Count)) { return(false); } AddFieldToUpdateLog(fieldName, stringVal, updateLog); processedFields.Add(fieldName); } AddLineToUpdateLog(updateLog); int attempt2Count = 0; if (!SetFieldValue(action, newRecord, NoteEntryFieldName, updateLog.ToString(), ref attempt2Count)) { return(false); } return(true); }
public void BatchSubmitLinkChange(LinkChangeGroup linkChanges) { if (linkChanges.Actions.Count == 0) { linkChanges.Status = LinkChangeGroup.LinkChangeGroupStatus.Completed; return; } // group changes by work item Id Dictionary <string, List <LinkChangeAction> > perRecordLinkChanges = RegroupLinkChangeActions(linkChanges); WorkItemLinkStore relatedArtifactsStore = new WorkItemLinkStore(m_configurationService.SourceId); // batch-submit links of each cq record bool successForAllActions = true; foreach (var perWorkItemLinkChange in perRecordLinkChanges) { string[] identity = UtilityMethods.ParseCQRecordMigrationItemId(perWorkItemLinkChange.Key); OAdEntity hostEntity = CQWrapper.GetEntity(m_userSession, identity[0], identity[1]); foreach (LinkChangeAction linkChangeAction in perWorkItemLinkChange.Value) { if (linkChangeAction.Status != LinkChangeAction.LinkChangeActionStatus.ReadyForMigration || linkChangeAction.IsConflicted) { continue; } var handler = linkChangeAction.Link.LinkType as ILinkHandler; Debug.Assert(null != handler, "linktype is not an ILinkHandler"); if (!handler.Update(m_migrationContext, m_userSession, hostEntity, linkChangeAction)) { successForAllActions = false; // [teyang] todo conflict handling linkChangeAction.Status = LinkChangeAction.LinkChangeActionStatus.Completed; linkChangeAction.IsConflicted = true; TraceManager.TraceError("Failed processing link change action: {0} linked to {1}", linkChangeAction.Link.SourceArtifact.Uri, linkChangeAction.Link.TargetArtifact.Uri); } else { MarkLinkChangeActionCompleted(linkChangeAction, relatedArtifactsStore); } } } linkChanges.Status = successForAllActions ? LinkChangeGroup.LinkChangeGroupStatus.Completed : LinkChangeGroup.LinkChangeGroupStatus.ReadyForMigration; }
private void SetFieldValue(OAdEntity entity, string fieldName, string fieldValue) { if (string.IsNullOrEmpty(fieldValue)) { return; } string retVal = CQWrapper.SetFieldValue(entity, fieldName, fieldValue); Trace.WriteIf(!string.IsNullOrEmpty(retVal), "retVal = " + retVal); Assert.IsTrue(string.IsNullOrEmpty(retVal), string.Format("SetFiledValue returned non-empty result : {0}, {1}", fieldName, fieldValue)); }
internal static int GetEntityFieldRequiredness(OAdEntity cqEntity, string fldName) { int retval = 0; try { retval = cqEntity.GetFieldRequiredness(fldName); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(retval); }
internal static string GetEntityDefName(OAdEntity cqEntity) { string entityDefName = null; try { entityDefName = cqEntity.GetEntityDefName(); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(entityDefName); }
public static string[] FindAllChangeActionNamesByType( Session userSession, OAdEntity entity, int changeType) { // find the entity type OAdEntityDef entityDef = CQWrapper.GetEntityDef(userSession, CQWrapper.GetEntityDefName(entity)); // find the MODIFY action def name to open the record object[] actionDefNames = CQWrapper.GetActionDefNames(entityDef) as object[]; string[] allValidActionNames = CQUtilityMethods.FindActionNameByType(entityDef, actionDefNames, changeType); return(allValidActionNames); }
internal static object GetFieldChoiceList(OAdEntity cqEntity, string fldName) { object choices = null; try { choices = cqEntity.GetFieldChoiceList(fldName); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(choices); }
internal static int GetFieldChoiceType(OAdEntity cqEntity, string fldName) { int choice = 0; try { choice = cqEntity.GetFieldChoiceType(fldName); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(choice); }
internal static object GetEntityFieldNames(OAdEntity cqEntity) { object fldNames = null; try { fldNames = cqEntity.GetFieldNames(); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(fldNames); }
internal static object GetDuplicates(OAdEntity cqEntity) { object retval = null; try { retval = cqEntity.GetDuplicates(); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(retval); }
internal static int GetEntityDbId(OAdEntity cqEntity) { int retVal = 0; try { retVal = cqEntity.GetDbId(); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(retVal); }
internal static bool HasDuplicates(OAdEntity cqEntity) { bool retval = false; try { retval = cqEntity.HasDuplicates(); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(retval); }
internal static string GetOriginalEntityId(OAdEntity cqEntity) { string retval = null; try { retval = cqEntity.GetOriginalId(); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(retval); }
internal static OAdEntity BuildEntity(Session cqSession, string entitydef_name) { OAdEntity entity = null; try { entity = (OAdEntity)cqSession.BuildEntity(entitydef_name); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(entity); }
internal static OAdEntity GetOriginalEntity(OAdEntity cqEntity) { OAdEntity retval = null; try { retval = (OAdEntity)cqEntity.GetOriginal(); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(retval); }
internal static OAdFieldInfo GetEntityFieldValue(OAdEntity cqEntity, string fldName) { OAdFieldInfo retval = null; try { retval = (OAdFieldInfo)cqEntity.GetFieldValue(fldName); } catch (COMException ex) { InteropErrorHandler.HandleCQException(ex); } return(retval); }