/// <summary> /// Creates a conflict of this type. /// </summary> /// <param name="path"></param> /// <returns></returns> public static MigrationConflict CreateConflict(string path, Node.TreeType treeType) { return(new MigrationConflict( new ExcessivePathConflictType(), MigrationConflict.Status.Unresolved, CreateConflictDetails(path, treeType), CreateScopeHint(path))); }
/// <summary> /// Creates path. /// </summary> /// <param name="type">Type of the node to be created</param> /// <param name="parentUri">Parent node</param> /// <param name="nodes">Node names</param> /// <param name="first">Index of the first node to create</param> /// <returns>Id of the node</returns> private int CreatePath( Node.TreeType type, string parentUri, string[] nodes, int first) { Debug.Assert(first < nodes.Length, "Nothing to create!"); // Step 1: create in CSS ICommonStructureService css = Css; for (int i = first; i < nodes.Length; i++) { string node = nodes[i]; if (!string.IsNullOrEmpty(node)) { try { parentUri = css.CreateNode(node, parentUri); } catch (CommonStructureSubsystemException cssEx) { if (cssEx.Message.Contains("TF200020")) { // TF200020 may be thrown if the tree node metadata has been propagated // from css to WIT cache. In this case, we will wait for the node id // Microsoft.TeamFoundation.Server.CommonStructureSubsystemException: // TF200020: The parent node already has a child node with the following name: {0}. // Child nodes must have unique names. Node existingNode = WaitForTreeNodeId(type, new string[] { node }); if (existingNode == null) { throw; } else { parentUri = existingNode.Uri.AbsoluteUri; } } } } } // Step 2: locate in the cache // Syncing nodes into WIT database is an asynchronous process, and there's no way to tell // the exact moment. Node newNode = WaitForTreeNodeId(type, nodes); if (newNode == null) { return(-1); } else { return(newNode.Id); } }
/// <summary> /// Constructor. /// </summary> /// <param name="nodeType">Type of the missing path</param> /// <param name="path">Missing path</param> /// <param name="message">Message to be associated with the exception</param> public MissingPathException( Node.TreeType nodeType, string path, string message) : base(message) { m_nodeType = nodeType; m_path = path; }
/// <summary> /// Translates string path into id. /// </summary> /// <param name="type">Path type (area/iteration)</param> /// <param name="path">Path to translate</param> /// <returns>Id of the node</returns> public int TranslatePath( Node.TreeType type, string path) { m_rwLock.AcquireReaderLock(-1); try { return(GetNode(type, path, true)); } finally { m_rwLock.ReleaseReaderLock(); } }
private Node WaitForTreeNodeId( Node.TreeType type, string[] nodes, int first) { int[] TIMEOUTS = { 100, 500, 1000, 5000 }; int[] RetryTimes = { 1, 2, 70, 36 }; for (int i = 0; i < TIMEOUTS.Length; ++i) { for (int k = 0; k < RetryTimes[i]; ++k) { System.Threading.Thread.Sleep(TIMEOUTS[i]); Debug.Write(string.Format("Wake up from {0} millisec sleep for polling CSS node Id", TIMEOUTS[i])); m_store.RefreshCache(); Project p = m_store.Projects[m_project.Name]; NodeCollection nc = type == Node.TreeType.Area ? p.AreaRootNodes : p.IterationRootNodes; Node n = null; int numNodesToCheck = nodes.Length - 1; if (first != -1) { numNodesToCheck = first; } try { for (int j = 0; j <= numNodesToCheck; j++) { string name = nodes[j]; if (!string.IsNullOrEmpty(name)) { n = nc[name]; nc = n.ChildNodes; } } return(n); } catch (DeniedOrNotExistException) { // The node is not there yet. Try one more time... } } } return(null); }
internal Node WaitForTreeNodeId( Node.TreeType type, string[] nodes) { int[] TIMEOUTS = { 100, 500, 1000, 5000 }; int[] RetryTimes = { 1, 2, 70, 36 }; for (int i = 0; i < TIMEOUTS.Length; ++i) { for (int k = 0; k < RetryTimes[i]; ++k) { Thread.Sleep(TIMEOUTS[i]); TraceManager.TraceInformation("Wake up from {0} millisec sleep for polling CSS node Id", TIMEOUTS[i]); m_store.RefreshCache(); Project p = m_store.Projects[m_cfg.Project]; NodeCollection nc = type == Node.TreeType.Area ? p.AreaRootNodes : p.IterationRootNodes; Node n = null; try { for (int j = 0; j < nodes.Length; j++) { string name = nodes[j]; if (!string.IsNullOrEmpty(name)) { n = nc[name]; nc = n.ChildNodes; } } return(n); } catch (DeniedOrNotExistException) { // The node is not there yet. Try one more time... } } } return(null); }
public static string CreateConflictDetails(string path, Node.TreeType treeType) { string pathType = "Unknown"; switch (treeType) { case Node.TreeType.Area: pathType = "Area Path"; break; case Node.TreeType.Iteration: pathType = "Iteration Path"; break; default: break; } return(string.Format("{0},{1}", pathType, path)); }
/// <summary> /// Get the Currituck field name from the Field Map /// </summary> /// <param name="from">Source field name</param> /// <param name="fvalue">Field value if changed because of some value map</param> /// <returns>Currituck Field Name</returns> private string GetMappedFieldName(string fName, ref object fValue) { string toval = string.Empty; FieldMapsFieldMap nmap = (FieldMapsFieldMap)m_fieldMappings[fName]; if (nmap != null) { FieldMapsFieldMapValueMaps fvmaps = null; toval = nmap.to; // check if there are value mappings for this field! if (nmap.ValueMaps != null) { fvmaps = nmap.ValueMaps; if (fvmaps.refer != null && !TFStringComparer.XmlAttributeValue.Equals(fvmaps.refer, "UserMap")) { fvmaps = (FieldMapsFieldMapValueMaps)m_valueMappings[nmap.ValueMaps.refer]; } if (TFStringComparer.XmlAttributeValue.Equals(fvmaps.refer, "UserMap")) { string currUser = fValue.ToString(); string toUser = currUser; if (m_userMappings != null && m_userMappings.UserMap != null) { foreach (UserMappingsUserMap userMap in m_userMappings.UserMap) { if (TFStringComparer.UserName.Equals(userMap.From, currUser)) { toUser = userMap.To; break; } } } if (m_vstsConnection.store.UserDisplayMode == UserDisplayMode.AccountName) { // for alias mode, no resolution is ever required fValue = toUser; } else { // resolve the user for Display Name mode if (VSTSUtil.ResolvedUsers.Contains(toUser)) { fValue = VSTSUtil.ResolvedUsers[toUser]; } else { Identity userIdentity = VSTSUtil.ResolveUser(m_vstsConnection, toUser); if (userIdentity == null) { CommonConstants.UnresolvedUsers.Append(string.Concat(toUser, ", ")); VSTSUtil.ResolvedUsers.Add(toUser, toUser); fValue = toUser; } else { VSTSUtil.ResolvedUsers.Add(toUser, userIdentity.DisplayName); fValue = userIdentity.DisplayName; } } } } else if (fvmaps.ValueMap != null) { int score = 0; ValueMap bestMatch = null; string fldVal = fValue.ToString(); foreach (ValueMap fvmap in fvmaps.ValueMap) { if (fldVal.StartsWith(fvmap.from, StringComparison.OrdinalIgnoreCase)) { // found one candidate if (fvmap.from.Length > score) { score = fvmap.from.Length; bestMatch = fvmap; } } } if (score > 0) { fValue = String.Concat(bestMatch.to, fValue.ToString().Substring(bestMatch.from.Length)); } } } // If it is Area Path, calculate the Area ID and update that field if (TFStringComparer.WorkItemFieldFriendlyName.Equals(nmap.to, VSTSConstants.AreaPathField) || TFStringComparer.WorkItemFieldFriendlyName.Equals(nmap.to, VSTSConstants.IterationPathField)) { Node.TreeType type = Node.TreeType.Area; if (TFStringComparer.WorkItemFieldFriendlyName.Equals(nmap.to, VSTSConstants.AreaPathField)) { toval = VSTSConstants.AreaIdField; type = Node.TreeType.Area; } else { toval = VSTSConstants.IterationIdField; type = Node.TreeType.Iteration; } Node tmpNode = null; string fValueStr = fValue.ToString().Trim(); if (fValueStr.Length != 0) { tmpNode = VSTSUtil.FindNodeInSubTree(m_vstsConnection, fValueStr, type); } if (tmpNode != null) { if (type == Node.TreeType.Area) { // update the current work item structure with this area id m_vstsWorkItem.areaId = tmpNode.Id; } fValue = tmpNode.Id; } else { if (fvmaps != null && fvmaps.defaultValue != null && fvmaps.defaultValue.Trim().Length > 0) { string defaultValueStr = fvmaps.defaultValue.Trim(); tmpNode = VSTSUtil.FindNodeInSubTree(m_vstsConnection, defaultValueStr, type); if (tmpNode != null) { Logger.Write(LogSource.WorkItemTracking, TraceLevel.Warning, UtilityMethods.Format( "Using: '{0}' instead of: '{1}' for: '{2}'", defaultValueStr, fValueStr, nmap.to)); ConverterMain.MigrationReport.WriteIssue("MigrationCheck", ReportIssueType.Info, UtilityMethods.Format( VSTSResource.UsingDefaultValue, defaultValueStr, fValueStr, nmap.to)); fValue = tmpNode.Id; } else { string errMsg = UtilityMethods.Format( VSTSResource.InvalidDefaultValueMap, m_sourceWorkItemId, nmap.to, fValueStr, m_fieldMapFile); throw new ConverterException(errMsg); } } else { string errMsg = UtilityMethods.Format( VSTSResource.NullDefaultValueMap, m_sourceWorkItemId, nmap.to, fValueStr, m_fieldMapFile); throw new ConverterException(errMsg); } } } } return(toval); }
/// <summary> /// Finds given node and returns its id. /// </summary> /// <param name="type">Node type (area/iteration)</param> /// <param name="path">Path to the node</param> /// <param name="respectPoliciesFlag">Tells whether policies should be respected in case the node is not found</param> /// <returns>Id of the node</returns> private int GetNode( Node.TreeType type, string path, bool respectPoliciesFlag) { string[] names = path.Split('\\'); Project p = m_store.Projects[m_cfg.Project]; NodeCollection nc = type == Node.TreeType.Area ? p.AreaRootNodes : p.IterationRootNodes; Node n = null; //WitMigrationConflictPolicy policy = type == Node.TreeType.Area ? m_missingArea : m_missingIteration; for (int i = 0; i < names.Length && !string.IsNullOrEmpty(names[i]); i++) { string name = names[i]; try { n = nc[name]; nc = n.ChildNodes; continue; } catch (DeniedOrNotExistException e) { string msg = string.Format( TfsWITAdapterResources.Culture, type == Node.TreeType.Area ? TfsWITAdapterResources.ErrorMissingArea : TfsWITAdapterResources.ErrorMissingIteration, p.Name + "\\" + path, m_name); TraceManager.TraceInformation(msg); if ((type == Node.TreeType.Area && DisableAreaPathAutoCreation) || (type == Node.TreeType.Iteration && DisableIterationPathAutoCreation)) { throw new MissingPathException(msg, e); } } //Debug.Assert(policy.Reaction != WitConflictReaction.Throw, "Invalid reaction!"); //if (policy.Reaction == WitConflictReaction.Default) //{ // return type == Node.TreeType.Area ? m_defaultAreaId : m_defaultIterationId; //} string parentUri; if (n == null) { parentUri = type == Node.TreeType.Area ? AreaNodeUri : IterationNodeUri; } else { parentUri = n.Uri.ToString(); } LockCookie cookie = m_rwLock.UpgradeToWriterLock(-1); try { int newId = CreatePath(type, parentUri, names, i); TraceManager.TraceInformation(string.Format( "Created path '{0}'(Id: {1}) in the TFS Work Item store '{2}'", p.Name + "\\" + path, newId, m_name)); return(newId); } finally { m_rwLock.DowngradeFromWriterLock(ref cookie); } } return(n == null ? m_projectId : n.Id); }
/// <summary> /// Handle catching DeniedOrNotExistException in case /// path looked up for is not found /// </summary> /// <param name="path"></param> /// <returns></returns> internal static Node FindNodeInSubTree(VSTSConnection vstsConn, string path, Node.TreeType type) { Node localNode = null; try { localNode = vstsConn.project.FindNodeInSubTree(path, type); } catch (DeniedOrNotExistException) { // try to create the given css path if (path.IndexOfAny(VSTSConstants.UnsupportedCSSChars) > -1) { String newPath = AreaPathRegEx.Replace(path, "_"); Logger.Write(LogSource.WorkItemTracking, TraceLevel.Warning, "Generating new CSS path from [{0}] to [{1}]", path, newPath); localNode = FindNodeInSubTree(vstsConn, newPath, type); } else { try { // try to create the CSS path if (Css == null) { Css = (ICommonStructureService)vstsConn.Tfs.GetService(typeof(ICommonStructureService)); } SetDefaultCSSUri(Css, vstsConn.projectName); if (type == Node.TreeType.Area) { CreateCSSPath(Css, path, RootAreaNodeUri); } else if (type == Node.TreeType.Iteration) { CreateCSSPath(Css, path, RootIterationNodeUri); } // after creating CSS path, sync the CSS tree if (VstsProjectInfo == null) { VstsProjectInfo = Css.GetProjectFromName(vstsConn.projectName); } WSHelper.SyncBisCSS(VstsProjectInfo); // refresh the connection vstsConn.Refresh(); // try to get the id now try { localNode = vstsConn.project.FindNodeInSubTree(path, type); } catch (DeniedOrNotExistException) { localNode = null; Logger.Write(LogSource.WorkItemTracking, TraceLevel.Warning, "Cannot find the CSS path {0} even after creating", path); } } finally { } } } return(localNode); }
public string Create( Node.TreeType type, string path) { if (string.IsNullOrEmpty(path)) { return(m_project.Name); } string[] names = path.Split('\\'); SanitizeNames(names); NodeCollection nc = type == Node.TreeType.Area ? m_project.AreaRootNodes : m_project.IterationRootNodes; Node n = null; int i = 0; if (string.CompareOrdinal(m_project.Name, names[0]) == 0) { i++; } for (; i < names.Length; i++) { string name = names[i]; if (string.IsNullOrEmpty(name)) { continue; } try { n = nc[name]; nc = n.ChildNodes; continue; } catch (DeniedOrNotExistException) { // Ignore this exception as we need to create the node if it does not exist. } string parentUri; if (n == null) { parentUri = type == Node.TreeType.Area ? m_areaNodeUri : m_iterationNodeUri; } else { parentUri = n.Uri.ToString(); } try { path = CreatePath(type, parentUri, names, i); } catch (SecurityException se) { throw new WorkItemMigratorException(se.Message + "\n\nNode::" + names[i] + "in " + path, null, null); } Debug.WriteLine( "Created path '{0}' in the TFS Work Item store '({1})'", m_project.Name + "\\" + path, m_project.Name); return(path); } return(n.Path); }
public static INode_TreeType GetWrapper(Node.TreeType src) { return(default(INode_TreeType)); }