Browse Source

Improved MbUnit addin.

git-svn-id: svn://svn.sharpdevelop.net/sharpdevelop/trunk@346 1ccf3a8d-04fe-1044-b7c0-cef0b8235c61
shortcuts
Daniel Grunwald 21 years ago
parent
commit
6316da8baf
  1. 16
      src/AddIns/Misc/MbUnitPad/Project/MbUnitPad.addin
  2. 8
      src/AddIns/Misc/MbUnitPad/Project/MbUnitPad.csproj
  3. 3
      src/AddIns/Misc/MbUnitPad/Project/MbUnitPad.csproj.user
  4. 33
      src/AddIns/Misc/MbUnitPad/Project/Src/MbUnitCommands.cs
  5. 23
      src/AddIns/Misc/MbUnitPad/Project/Src/MbUnitPad.cs
  6. 78
      src/AddIns/Misc/MbUnitPad/Project/Src/TestTreeView.cs
  7. 11
      src/Main/StartUp/Project/Dialogs/ExceptionBox.cs
  8. 39
      src/Main/StartUp/Project/SharpDevelopMain.cs

16
src/AddIns/Misc/MbUnitPad/Project/MbUnitPad.addin

@ -14,7 +14,7 @@
<Path name = "/SharpDevelop/Workbench/Pads"> <Path name = "/SharpDevelop/Workbench/Pads">
<Pad id = "MbUnitPad" <Pad id = "MbUnitPad"
category = "Main" category = "Main"
title = "Unit Tests" title = "MbUnit Tests"
icon = "PadIcons.UnitTest" icon = "PadIcons.UnitTest"
shortcut = "Control|Alt|T" shortcut = "Control|Alt|T"
class = "MbUnitPad.MbUnitPadContent"/> class = "MbUnitPad.MbUnitPadContent"/>
@ -26,6 +26,20 @@
icon = "Icons.16x16.BrowserRefresh" icon = "Icons.16x16.BrowserRefresh"
tooltip = "${res:NUnitPad.NUnitPadContent.RefreshItem}" tooltip = "${res:NUnitPad.NUnitPadContent.RefreshItem}"
class = "MbUnitPad.ReloadCommand"/> class = "MbUnitPad.ReloadCommand"/>
<ToolbarItem id = "Unload"
icon = "Icons.16x16.BrowserCancel"
tooltip = "${res:NUnitPad.NUnitPadContent.UnloadItem}"
class = "MbUnitPad.UnloadCommand"/>
<ToolbarItem id = "Separator1" type = "Separator"/>
<ToolbarItem id = "AddMbUnitReference"
icon = "Icons.16x16.Reference"
tooltip = "Add reference to MbUnit."
class = "MbUnitPad.AddMbUnitReferenceCommand"/>
<ToolbarItem id = "AddNUnitReference"
icon = "PadIcons.UnitTest"
tooltip = "NUnitPad.NUnitPadContent.ReferenceItem"
class = "MbUnitPad.AddNUnitReferenceCommand"/>
<ToolbarItem id = "Separator2" type = "Separator"/>
<ToolbarItem id = "Run" <ToolbarItem id = "Run"
icon = "Icons.16x16.RunProgramIcon" icon = "Icons.16x16.RunProgramIcon"
tooltip = "${res:NUnitPad.NUnitPadContent.RunItem}" tooltip = "${res:NUnitPad.NUnitPadContent.RunItem}"

8
src/AddIns/Misc/MbUnitPad/Project/MbUnitPad.csproj

@ -6,13 +6,15 @@
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration> <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform> <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>{B1CE28A0-04E8-490D-8256-E0C4D52C93C8}</ProjectGuid> <ProjectGuid>{B1CE28A0-04E8-490D-8256-E0C4D52C93C8}</ProjectGuid>
<ProductVersion>8.0.50215</ProductVersion>
<SchemaVersion>2.0</SchemaVersion>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' "> <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<OutputPath>..\..\..\..\..\AddIns\AddIns\Misc\MbUnitPad\</OutputPath> <OutputPath>..\..\..\..\..\AddIns\AddIns\Misc\MbUnitPad\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants> <DefineConstants>DEBUG;TRACE</DefineConstants>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' "> <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<OutputPath>bin\Release\</OutputPath> <OutputPath>..\..\..\..\..\AddIns\AddIns\Misc\MbUnitPad\</OutputPath>
<Optimize>true</Optimize> <Optimize>true</Optimize>
<DefineConstants>TRACE</DefineConstants> <DefineConstants>TRACE</DefineConstants>
</PropertyGroup> </PropertyGroup>
@ -40,7 +42,9 @@
<Compile Include="Src\MbUnitPad.cs" /> <Compile Include="Src\MbUnitPad.cs" />
<Compile Include="Configuration\AssemblyInfo.cs" /> <Compile Include="Configuration\AssemblyInfo.cs" />
<Compile Include="Src\MbUnitCommands.cs" /> <Compile Include="Src\MbUnitCommands.cs" />
<Compile Include="Src\TestTreeView.cs" /> <Compile Include="Src\TestTreeView.cs">
<SubType>UserControl</SubType>
</Compile>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<ProjectReference Include="..\..\..\..\Main\Base\Project\ICSharpCode.SharpDevelop.csproj"> <ProjectReference Include="..\..\..\..\Main\Base\Project\ICSharpCode.SharpDevelop.csproj">

3
src/AddIns/Misc/MbUnitPad/Project/MbUnitPad.csproj.user

@ -1,3 +1,6 @@
<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' " /> <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' " />
<PropertyGroup>
<LastOpenVersion>8.0.50215</LastOpenVersion>
</PropertyGroup>
</Project> </Project>

33
src/AddIns/Misc/MbUnitPad/Project/Src/MbUnitCommands.cs

@ -8,6 +8,7 @@
using System; using System;
using ICSharpCode.Core; using ICSharpCode.Core;
using ICSharpCode.SharpDevelop; using ICSharpCode.SharpDevelop;
using ICSharpCode.SharpDevelop.Project;
using MbUnit.Forms; using MbUnit.Forms;
namespace MbUnitPad namespace MbUnitPad
@ -20,11 +21,41 @@ namespace MbUnitPad
} }
} }
public class UnloadCommand : AbstractMenuCommand
{
public override void Run()
{
MbUnitPadContent.Instance.TreeView.RemoveAssemblies();
}
}
public class RunTestsCommand : AbstractMenuCommand public class RunTestsCommand : AbstractMenuCommand
{ {
public override void Run() public override void Run()
{ {
MbUnitPadContent.Instance.TreeView.ThreadedRunTests(); MbUnitPadContent.Instance.RunTests();
}
}
public class AddNUnitReferenceCommand : AbstractMenuCommand
{
public override void Run()
{
if (ProjectService.CurrentProject != null) {
ProjectService.AddProjectItem(ProjectService.CurrentProject, new ReferenceProjectItem(ProjectService.CurrentProject, "nunit.framework"));
ProjectService.CurrentProject.Save();
}
}
}
public class AddMbUnitReferenceCommand : AbstractMenuCommand
{
public override void Run()
{
if (ProjectService.CurrentProject != null) {
ProjectService.AddProjectItem(ProjectService.CurrentProject, new ReferenceProjectItem(ProjectService.CurrentProject, "MbUnit.Framework"));
ProjectService.CurrentProject.Save();
}
} }
} }
} }

23
src/AddIns/Misc/MbUnitPad/Project/Src/MbUnitPad.cs

@ -67,13 +67,29 @@ namespace MbUnitPad
void OnSolutionClosed(object sender, EventArgs e) void OnSolutionClosed(object sender, EventArgs e)
{ {
LoggingService.Info("Solution closed"); treeView.NewConfig();
treeView.RemoveAssemblies(); }
public void RunTests()
{
if (treeView.TypeTree.Nodes.Count == 0) {
treeView.TreePopulated += StartTestsAfterTreePopulation;
ReloadAssemblyList();
} else {
treeView.ThreadedRunTests();
}
}
void StartTestsAfterTreePopulation(object sender, EventArgs e)
{
treeView.TreePopulated -= StartTestsAfterTreePopulation;
// we cannot run the tests on this thread because we have to wait for the worker thread to exit
WorkbenchSingleton.SafeThreadAsyncCall(treeView, "ThreadedRunTests");
} }
public void ReloadAssemblyList() public void ReloadAssemblyList()
{ {
treeView.RemoveAssemblies(); treeView.TestDomains.Clear();
foreach (IProject project in ProjectService.OpenSolution.Projects) { foreach (IProject project in ProjectService.OpenSolution.Projects) {
bool referenceFound = false; bool referenceFound = false;
foreach (ProjectItem item in project.Items) { foreach (ProjectItem item in project.Items) {
@ -105,6 +121,7 @@ namespace MbUnitPad
} }
} }
} }
treeView.ThreadedPopulateTree(true);
} }
/// <summary> /// <summary>

78
src/AddIns/Misc/MbUnitPad/Project/Src/TestTreeView.cs

@ -6,20 +6,98 @@
// </file> // </file>
using System; using System;
using System.Collections;
using System.IO;
using System.Reflection;
using System.Windows.Forms; using System.Windows.Forms;
using ICSharpCode.Core; using ICSharpCode.Core;
using ICSharpCode.SharpDevelop.Gui;
using MbUnit.Forms; using MbUnit.Forms;
using MbUnit.Core;
using MbUnit.Core.Remoting; using MbUnit.Core.Remoting;
using MbUnit.Core.Reports.Serialization;
namespace MbUnitPad namespace MbUnitPad
{ {
public class TestTreeView : ReflectorTreeView public class TestTreeView : ReflectorTreeView
{ {
Hashtable pipeNodes;
public TestTreeView() public TestTreeView()
{ {
TypeTree.ContextMenu = null; TypeTree.ContextMenu = null;
TypeTree.ContextMenuStrip = MenuService.CreateContextMenu(this, "/MbUnitPad/ContextMenu"); TypeTree.ContextMenuStrip = MenuService.CreateContextMenu(this, "/MbUnitPad/ContextMenu");
this.StartTests += OnTestsStarted;
this.FinishTests += delegate { BeginInvoke(new MethodInvoker(ExpandAllFailures)); };
this.Facade.Updated += OnFacadeUpdated;
// I don't see another good way to get a pipe node by GUID but stealing the facade's hashtable
pipeNodes = (Hashtable)typeof(TestTreeNodeFacade).InvokeMember("pipeNodes", BindingFlags.GetField | BindingFlags.Instance | BindingFlags.NonPublic, null, Facade, null);
}
static MessageViewCategory testRunnerCategory;
void OnTestsStarted(object sender, EventArgs e)
{
BeginInvoke(new EventHandler(OnTestsStartedInvoked));
}
void OnTestsStartedInvoked(object sender, EventArgs e)
{
if (testRunnerCategory == null) {
testRunnerCategory = new MessageViewCategory("MbUnit");
CompilerMessageView cmv = (CompilerMessageView)WorkbenchSingleton.Workbench.GetPad(typeof(CompilerMessageView)).PadContent;
cmv.AddCategory(testRunnerCategory);
} else {
testRunnerCategory.ClearText();
}
}
void OnFacadeUpdated(ResultEventArgs e)
{
try {
if (e.State == TestState.Failure) {
IList list = (IList)pipeNodes[e.PipeIdentifier];
for (int i = 0; i < list.Count; i++) {
UnitTreeNode node = list[i] as UnitTreeNode;
if (node != null) {
AppendResult(this.TestDomains.GetResult(node));
break;
} }
}
}
} catch (Exception ex) {
MessageService.ShowError(ex);
}
}
void AppendResult(ReportRun result)
{
ReportException ex = result.Exception;
string message = (ex != null) ? ex.Message : "-";
string outputMessage = StringParser.Parse("${res:NUnitPad.NUnitPadContent.TestTreeView.TestFailedMessage}", new string[,] {
{"TestCase", result.Name},
{"Message", message}
});
testRunnerCategory.AppendText(outputMessage + Environment.NewLine);
testRunnerCategory.AppendText(result.Description + Environment.NewLine);
if (ex != null) {
testRunnerCategory.AppendText(ex.StackTrace + Environment.NewLine);
FileLineReference LineRef = OutputTextLineParser.GetNUnitOutputFileLineReference(ex.StackTrace, true);
if (LineRef != null) {
Task task = new Task(Path.GetFullPath(LineRef.FileName),
outputMessage,
LineRef.Column,
LineRef.Line,
TaskType.Error);
BeginInvoke(new AddTaskInvoker(TaskService.Add), new object[] { task });
}
}
}
delegate void AddTaskInvoker(Task task);
/// <summary> /// <summary>
/// Default MbUnit-GUI doesn't use shadow copy, we have to override that behaviour. /// Default MbUnit-GUI doesn't use shadow copy, we have to override that behaviour.

11
src/Main/StartUp/Project/Dialogs/ExceptionBox.cs

@ -30,17 +30,24 @@ namespace ICSharpCode.SharpDevelop
Exception exceptionThrown; Exception exceptionThrown;
string message; string message;
public ExceptionBox(Exception e, string message) public ExceptionBox(Exception e, string message, bool mustTerminate)
{ {
this.exceptionThrown = e; this.exceptionThrown = e;
this.message = message; this.message = message;
InitializeComponent(); InitializeComponent();
RightToLeftConverter.Convert(this); if (mustTerminate) {
closeButton.Visible = false;
continueButton.Text = closeButton.Text;
continueButton.Left -= closeButton.Width - continueButton.Width;
continueButton.Width = closeButton.Width;
}
exceptionTextBox.Text = getClipboardString(); exceptionTextBox.Text = getClipboardString();
try {
ResourceManager resources = new ResourceManager("Resources.BitmapResources", Assembly.GetEntryAssembly()); ResourceManager resources = new ResourceManager("Resources.BitmapResources", Assembly.GetEntryAssembly());
this.pictureBox.Image = (Bitmap)resources.GetObject("ErrorReport"); this.pictureBox.Image = (Bitmap)resources.GetObject("ErrorReport");
} catch {}
} }
string getClipboardString() string getClipboardString()

39
src/Main/StartUp/Project/SharpDevelopMain.cs

@ -39,21 +39,40 @@ namespace ICSharpCode.SharpDevelop
} }
} }
static void ShowErrorBox(object sender, ThreadExceptionEventArgs eargs) static void ShowErrorBox(object sender, ThreadExceptionEventArgs e)
{ {
LoggingService.Error("ThreadException caught", eargs.Exception); LoggingService.Error("ThreadException caught", e.Exception);
ShowErrorBox(eargs.Exception, null); ShowErrorBox(e.Exception, null);
}
static void ShowErrorBox(object sender, UnhandledExceptionEventArgs e)
{
Exception ex = e.ExceptionObject as Exception;
LoggingService.Fatal("UnhandledException caught", ex);
if (e.IsTerminating)
LoggingService.Fatal("Runtime is terminating because of unhandled exception.");
ShowErrorBox(ex, "Unhandled exception", e.IsTerminating);
} }
static void ShowErrorBox(Exception exception, string message) static void ShowErrorBox(Exception exception, string message)
{ {
using (ExceptionBox box = new ExceptionBox(exception, message)) { ShowErrorBox(exception, message, false);
DialogResult result = box.ShowDialog(ICSharpCode.SharpDevelop.Gui.WorkbenchSingleton.MainForm); }
if (result == DialogResult.Abort) { static void ShowErrorBox(Exception exception, string message, bool mustTerminate)
Application.Exit(); {
try {
using (ExceptionBox box = new ExceptionBox(exception, message, mustTerminate)) {
try {
box.ShowDialog(ICSharpCode.SharpDevelop.Gui.WorkbenchSingleton.MainForm);
} catch (InvalidOperationException) {
box.ShowDialog();
} }
} }
} catch (Exception ex) {
LoggingService.Warn("Error showing ExceptionBox", ex);
MessageBox.Show(exception.ToString());
}
} }
/// <summary> /// <summary>
@ -80,7 +99,7 @@ namespace ICSharpCode.SharpDevelop
{ {
LoggingService.Fatal(ex); LoggingService.Fatal(ex);
try { try {
Application.Run(new ExceptionBox(ex, "Unhandled exception terminated SharpDevelop")); Application.Run(new ExceptionBox(ex, "Unhandled exception terminated SharpDevelop", true));
} catch { } catch {
MessageBox.Show(ex.ToString(), "Critical error (cannot use ExceptionBox)"); MessageBox.Show(ex.ToString(), "Critical error (cannot use ExceptionBox)");
} }
@ -127,10 +146,12 @@ namespace ICSharpCode.SharpDevelop
{ {
LoggingService.Info("Starting SharpDevelop..."); LoggingService.Info("Starting SharpDevelop...");
try { try {
#if DEBUG
if (!Debugger.IsAttached) { if (!Debugger.IsAttached) {
Application.ThreadException += ShowErrorBox; Application.ThreadException += ShowErrorBox;
AppDomain.CurrentDomain.UnhandledException += ShowErrorBox;
} }
#if !DEBUG #else
MessageService.CustomErrorReporter = ShowErrorBox; MessageService.CustomErrorReporter = ShowErrorBox;
#endif #endif

Loading…
Cancel
Save