/// <summary> /// Extracts error data from an ErrorWarningCode object and /// puts it into a Hashtable as a set of key-value pairs. /// ErrorWarningCode object represents an error or warning from MSBuild. /// </summary> /// <param name="e"></param> /// <returns>Hashtable containing the error data as a set of key-value pairs</returns> public static Hashtable ExtractErrData(ErrorWarningCode e) { Hashtable errData = new Hashtable(); errData["ErrorMessage"] = e.Description; errData["Line"] = e.LineNumber.ToString(); errData["Position"] = e.ColumnNumber.ToString(); return(errData); }
/// <summary> /// Some errors do not come with Error ID's or Warning ID's. /// Example MSBuild <Error></Error> & <Warning></Warning> elements. /// To support this I am creating this hack to check only the description based /// on Partial flag set to false. /// </summary> /// <param name="currentdescription"></param> /// <returns></returns> internal bool CheckUnassignedDescriptionExists(string currentdescription) { if (expectederrors == null || expectederrors.Count == 0) { return(false); } IDictionaryEnumerator enumerator = expectederrors.GetEnumerator(); while (enumerator.MoveNext()) { ErrorWarningCode ewc = (ErrorWarningCode)enumerator.Value; if (String.IsNullOrEmpty(ewc.Description) == false) { if (ewc.Description.ToLowerInvariant() == currentdescription.ToLowerInvariant()) { if (ewc.IsIgnoreable) { ewc = null; goto SuccessFullExit; } } else if (currentdescription.ToLowerInvariant().Contains(ewc.Description.ToLowerInvariant())) { if (ewc.IsIgnoreable && ewc.IsPartial) { ewc = null; goto SuccessFullExit; } } else if (ErrorWarningCode.Compare(ewc.description, currentdescription)) { if (ewc.IsIgnoreable) { ewc = null; goto SuccessFullExit; } } } } enumerator = null; return(false); SuccessFullExit: enumerator = null; return(true); }
/// <summary> /// Build Finished Event handler, logs to build log file. /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void eventSource_BuildFinishedEvent(object sender, BuildFinishedEventArgs e) { LogToBuildLog(e.Message); if (logmemorystream != null) { MSBuildEngineCommonHelper.WritetoFilefromMemory(ref logmemorystream, this.buildlogfile); } if (errormemorystream != null) { MSBuildEngineCommonHelper.WritetoFilefromMemory(ref errormemorystream, this.builderrorfile); } if (warningmemorystream != null) { MSBuildEngineCommonHelper.WritetoFilefromMemory(ref warningmemorystream, this.buildwaringfile); } projectfilestack = null; currentduplicateerrorwarningid = null; }
/// <summary> /// Find a particular error code and return the object. /// If nothing with the id was found, return null. /// </summary> /// <param name="errorid"></param> /// <returns></returns> internal ErrorWarningCode this[string errorid] { get { MSBuildEngineCommonHelper.LogDiagnostic = "GetErrorDescription -"; if (String.IsNullOrEmpty(errorid.ToUpper())) { MSBuildEngineCommonHelper.LogDiagnostic = "Input value was null"; return(null); } ErrorWarningCode ewc = (ErrorWarningCode)errorcodes[errorid.ToUpper()]; if (ewc == null) { return(null); } return(ewc); } }
/// <summary> /// Set a warning or error in the Error XML file as ignoreable dynamically. /// This method is used to set existing parsed errors + warnings from the error file /// as ignoreable. /// This enables the testing where certain error's or warnings can be ignored. /// </summary> /// <param name="errorid">Error/Warning ID that exists in Error file</param> /// <param name="ignoreable">Boolean value to set Ignoreable property on Error/Warning</param> internal void SetErrorWarningAsIgnoreable(string errorid, bool ignoreable) { if (String.IsNullOrEmpty(errorid)) { MSBuildEngineCommonHelper.LogDiagnostic = "SetErrorWarningAsIgnoreable - Input paramter errorid is null"; return; } if (listoferrorwarningswithoutid == null) { listoferrorwarningswithoutid = new List <string>(); } if (errorid.StartsWith("LH") || errorid.StartsWith("UN")) { listoferrorwarningswithoutid.Add(errorid.ToUpper()); } ErrorWarningCode desiredewc = (ErrorWarningCode)expectederrors[errorid.ToUpper()]; if (desiredewc == null) { MSBuildEngineCommonHelper.Log = "Could not find error/warning for corresponding error id - " + errorid; return; } // If the error/warning is already set to ignore don't do anything. if (desiredewc.IsIgnoreable) { MSBuildEngineCommonHelper.Log = "SetErrorWarningAsIgnoreable - Current error/warning is set to Ignoreable already."; return; } expectederrors.Remove(errorid.ToUpper()); desiredewc.IsIgnoreable = ignoreable; expectederrors.Add(errorid.ToUpper(), desiredewc); }
/// <summary> /// This is specific handling for duplicated Error/Warning ID's. /// </summary> /// <param name="actualerrorwarning"></param> /// <returns></returns> private bool IsDuplicatedErrorMessageIgnorable(ref ErrorWarningCode actualerrorwarning) { if (actualerrorwarning == null) { return(false); } ErrorWarningCode tempewc = null; IDictionaryEnumerator enumerator = expectederrors.GetEnumerator(); while (enumerator.MoveNext()) { if (enumerator.Key.ToString().StartsWith(actualerrorwarning.ID)) { tempewc = (ErrorWarningCode)enumerator.Value; if (tempewc == null) { tempewc = null; continue; } if (String.IsNullOrEmpty(tempewc.Description)) { tempewc = null; continue; } if (actualerrorwarning.Description.Contains(tempewc.Description)) { break; } if (ErrorWarningCode.Compare(tempewc.description, actualerrorwarning.Description)) { currentduplicateerrorwarningid = actualerrorwarning; tempewc = null; enumerator = null; return(true); } tempewc = null; } } // Should never happen! if (tempewc == null) { return(false); } if (actualerrorwarning.Equals(tempewc) == false) { return(false); } currentduplicateerrorwarningid = tempewc; tempewc = null; enumerator = null; return(currentduplicateerrorwarningid.IsIgnoreable); }
/// <summary> /// Method checks if the error/warning exists in the ErrorWarnings list using error id. /// If the error is found verify description depending on IsPartial attribute value. /// Also if error is found check if IsIgnoreable attribute set to true /// </summary> /// <param name="e">BuildEventArgs object from MSBuild</param> /// <param name="errortype">Error or Warning</param> /// <returns></returns> private bool IsErrorMessageIgnorable(BuildEventArgs e, string errortype) { MSBuildEngineCommonHelper.LogDiagnostic = "Executing Find Error message"; if (expectederrors == null && _berrorhandling == true) { // This is when there is no error file specified. return(false); } if (String.IsNullOrEmpty(e.Message)) { return(false); } string errorid = null; BuildWarningEventArgs warningeventargs = null; BuildErrorEventArgs erroreventargs = e as BuildErrorEventArgs; if (erroreventargs == null) { warningeventargs = e as BuildWarningEventArgs; if (warningeventargs == null) { throw new ApplicationException("Type of Build event could not be determined."); } errorid = warningeventargs.Code; } else { errorid = erroreventargs.Code; } ErrorWarningCode actualerrorwarning = new ErrorWarningCode(e); if (_listofhandlederrors == null) { _listofhandlederrors = new List <ErrorWarningCode>(); } _listofhandlederrors.Add(actualerrorwarning); if (!_berrorhandling) { return(false); } if (String.IsNullOrEmpty(errorid)) { errorid = actualerrorwarning.ID; } // Retired. //if (String.IsNullOrEmpty(errorid)) //{ // // Currently in Avalon the implementation is not in line with reporting // // Code ID, Line #, Position and so on. // // Adding work around here. // //MSBuildEngineCommonHelper.Log = "Could not find Error/Warning with ID - " + errorid; // return IsAvalonErrorMessageIgnorable(e, errortype); // //return false; //} if (String.IsNullOrEmpty(errorid)) { if (CheckUnassignedDescriptionExists(e.Message) == false) { //if (listofhandlederrors == null) //{ // listofhandlederrors = new List<string>(); //} //if (listofhandlederrors.Contains(currentduplicateerrorwarningid) == false) //{ // listofhandlederrors.Add(e.Message); //} MSBuildEngineCommonHelper.LogError = "Build error/warning should contain an error ID."; return(false); } else { if (listoferrorwarningswithoutid != null) { for (int i = 0; i < listoferrorwarningswithoutid.Count; i++) { string erroridwithoutdescription = listoferrorwarningswithoutid[i]; if (erroridwithoutdescription.ToLowerInvariant().Contains("_Dup".ToLowerInvariant())) { int index = erroridwithoutdescription.ToLowerInvariant().IndexOf("_Dup".ToLowerInvariant()); erroridwithoutdescription = erroridwithoutdescription.Substring(0, index); } if (listoferrorwarningswithoutid.Contains(erroridwithoutdescription)) { listoferrorwarningswithoutid.RemoveAt(i); if (listoferrorwarningswithoutid.Count > 0 && i > 0) { i--; } _listofhandlederrors.Remove(actualerrorwarning); //break; } } // Todo: } return(true); } } if (IsDuplicated(errorid.ToUpper())) { if (IsDuplicatedErrorMessageIgnorable(ref actualerrorwarning)) { if (_listofhandlederrors != null && _listofhandlederrors.Contains(currentduplicateerrorwarningid)) //if (_listofhandlederrors != null) { //for (int i = 0; i < _listofhandlederrors.Count; i++) //{ // if (_listofhandlederrors[i].Equals(currentduplicateerrorwarningid)) // { _listofhandlederrors.Remove(currentduplicateerrorwarningid); // } //} } currentduplicateerrorwarningid = null; return(true); } else { currentduplicateerrorwarningid = null; return(false); } } if (expectederrors[errorid.ToUpper()] == null) { return(false); } // Get object based on error id. ErrorWarningCode desirederrorwarning = (ErrorWarningCode)expectederrors[errorid.ToUpper()]; if (desirederrorwarning == null) { MSBuildEngineCommonHelper.Log = "Could not find Error/Warning with ID - " + errorid; return(false); } if (actualerrorwarning.Equals(desirederrorwarning) == false) { return(false); } if (_listofhandlederrors != null && _listofhandlederrors.Count > 0 && _listofhandlederrors.Contains(actualerrorwarning)) { _listofhandlederrors.Remove(actualerrorwarning); } actualerrorwarning = null; return(desirederrorwarning.IsIgnoreable); }
/// <summary> /// Override of Equals to do ErrorWarningCode specific comparison. /// </summary> /// <param name="obj"></param> /// <returns></returns> public override bool Equals(object obj) { ErrorWarningCode parsederrorwarningcode = (ErrorWarningCode)obj; if (parsederrorwarningcode == null) { return(false); } // Simple check to see if Full Description of Expected and Actual are the same. if (this.FullDescription == parsederrorwarningcode.FullDescription) { return(true); } // Check for error ID, if it doesn't match return failure. if (this.id != parsederrorwarningcode.id) { if (parsederrorwarningcode.id.ToString().StartsWith(this.id) == false) { MSBuildEngineCommonHelper.LogDiagnostic = "Expected and Actual ID's are different"; MSBuildEngineCommonHelper.LogDiagnostic = "Expected ID Value : " + parsederrorwarningcode.id; MSBuildEngineCommonHelper.LogDiagnostic = "Actual ID Value : " + this.id; return(false); } } if (this.linenumber != parsederrorwarningcode.linenumber && parsederrorwarningcode.bpartial == true) { if (parsederrorwarningcode.bpartial == false) { MSBuildEngineCommonHelper.LogWarning = "Expected and Actual Line Numbers are different"; MSBuildEngineCommonHelper.LogWarning = "Expected Line Number Value : " + parsederrorwarningcode.linenumber; MSBuildEngineCommonHelper.LogWarning = "Actual Line Number Value : " + this.linenumber; } } if (this.offsetnumber != parsederrorwarningcode.offsetnumber && parsederrorwarningcode.bpartial == true) { if (parsederrorwarningcode.bpartial == false) { MSBuildEngineCommonHelper.LogWarning = "Expected and Actual Column Numbers are different"; MSBuildEngineCommonHelper.LogWarning = "Expected Column Number Value : " + parsederrorwarningcode.offsetnumber; MSBuildEngineCommonHelper.LogWarning = "Actual Column Number Value : " + this.offsetnumber; } } if (String.IsNullOrEmpty(parsederrorwarningcode.source) == false) { //if (expectederrorwarningcode.IsPartial == false) //{ MSBuildEngineCommonHelper.Log = "Expected error/warning does not define a Source value."; // return false; //} if (this.source.ToLowerInvariant() != parsederrorwarningcode.source.ToLowerInvariant()) { MSBuildEngineCommonHelper.LogDiagnostic = "Expected and Actual sources are different"; MSBuildEngineCommonHelper.LogDiagnostic = "Expected Source Value : " + parsederrorwarningcode.source; MSBuildEngineCommonHelper.LogDiagnostic = "Actual Source Value : " + this.source; return(false); } } if (String.IsNullOrEmpty(parsederrorwarningcode.startingmessage) == false) { //if (expectederrorwarningcode.IsPartial == false) //{ MSBuildEngineCommonHelper.LogDiagnostic = "Expected error/warning does not define a Starting Message value."; // return false; //} if (this.startingmessage != parsederrorwarningcode.startingmessage) { if (parsederrorwarningcode.bpartial == false) { MSBuildEngineCommonHelper.LogError = "Expected and Actual Starting Message are different"; MSBuildEngineCommonHelper.LogError = "Expected Starting Message Value : " + parsederrorwarningcode.startingmessage; MSBuildEngineCommonHelper.LogError = "Actual Starting Message Value : " + this.startingmessage; return(false); } } } if (parsederrorwarningcode.description == null) { MSBuildEngineCommonHelper.Log = "Expected error/warning does not define a Description value."; return(false); } if (parsederrorwarningcode.description.Length == 0) { MSBuildEngineCommonHelper.Log = "Expected error/warning does not define a Description value."; return(false); } if (this.Description != parsederrorwarningcode.Description) { if (parsederrorwarningcode.bpartial || parsederrorwarningcode.ignoreable) { if (parsederrorwarningcode.description.Length > 1) { if (Compare(parsederrorwarningcode.description, this.description[0]) == false) { return(false); } } else { int index = this.FullDescription.IndexOf(parsederrorwarningcode.Description); if (index < 0) { MSBuildEngineCommonHelper.Log = "Expected error/warning does not match the actual error/warning description."; return(false); } } } else { MSBuildEngineCommonHelper.Log = "Expected error/warning does not match the actual error/warning description."; return(false); } } return(parsederrorwarningcode.IsIgnoreable); }
/// <summary> /// /// </summary> /// <param name="errorwarningelem"></param> internal void Parse(XmlElement errorwarningelem) { // Get a Xml list of errors and convert them into ErrorWarningCodes objects // and them into the _errorcodes list. XmlNodeList nodelist = errorwarningelem.GetElementsByTagName(Constants.ErrorElement); if (nodelist.Count == 0) { MSBuildEngineCommonHelper.LogDiagnostic = "No Error descriptions found in "; } else { // Set the capacity of the _errorcodes list to the nodelist count. // Removed :_errorcodes.Capacity = nodelist.Count; for (int i = 0; i < nodelist.Count; i++) { ErrorWarningCode ec = new ErrorWarningCode(nodelist[i]); if (errorcodes.Contains(ec.ID)) { //string newid = ec.ID + "_Dup" + new Random().Next(1000).ToString(); //ec.ID = newid; if (ec.ReferredID != ec.ID) { errorcodes.Add(ec.ReferredID.ToUpper(), ec); continue; } } errorcodes.Add(ec.ID.ToUpper(), ec); } } // Get a Xml list of warnings and convert them into ErrorWarningCodes objects // and them into the _errorcodes list. nodelist = errorwarningelem.GetElementsByTagName(Constants.WarningElement); if (nodelist.Count > 0) { // Set the capacity of the _errorcodes list to the nodelist count. // Removed : _errorcodes.Capacity += nodelist.Count; for (int i = 0; i < nodelist.Count; i++) { ErrorWarningCode ec = new ErrorWarningCode(nodelist[i]); if (errorcodes.Contains(ec.ID)) { //string newid = ec.ID + "_Dup" + new Random().Next(1000).ToString(); //ec.ID = newid; if (ec.ReferredID != ec.ID) { errorcodes.Add(ec.ReferredID.ToUpper(), ec); continue; } } errorcodes.Add(ec.ID.ToUpper(), ec); } } else { MSBuildEngineCommonHelper.LogDiagnostic = "No Warning descriptions found."; } MSBuildEngineCommonHelper.LogDiagnostic = "Done Parsing Error/Warning file"; }