diff --git a/src/CodingWithCalvin.SuperClean/CodingWithCalvin.SuperClean.csproj b/src/CodingWithCalvin.SuperClean/CodingWithCalvin.SuperClean.csproj
index 322ec51..a19c06d 100644
--- a/src/CodingWithCalvin.SuperClean/CodingWithCalvin.SuperClean.csproj
+++ b/src/CodingWithCalvin.SuperClean/CodingWithCalvin.SuperClean.csproj
@@ -8,11 +8,8 @@
bin/$(Configuration)/
-
- True
-
-
+
diff --git a/src/CodingWithCalvin.SuperClean/Commands/SuperCleanCommand.cs b/src/CodingWithCalvin.SuperClean/Commands/SuperCleanCommand.cs
index 90f9081..9834d79 100644
--- a/src/CodingWithCalvin.SuperClean/Commands/SuperCleanCommand.cs
+++ b/src/CodingWithCalvin.SuperClean/Commands/SuperCleanCommand.cs
@@ -1,8 +1,10 @@
-using System;
+using System;
+using System.Collections.Generic;
using System.ComponentModel.Design;
using System.IO;
using System.Text;
using System.Threading.Tasks;
+using CodingWithCalvin.Otel4Vsix;
using Community.VisualStudio.Toolkit;
using Microsoft.VisualStudio.Shell;
using MessageBox = System.Windows.Forms.MessageBox;
@@ -42,12 +44,20 @@ public static void Initialize(Package package)
private static void OpenPathWrapper(object sender, EventArgs e)
{
+ using var activity = VsixTelemetry.StartCommandActivity("SuperClean.OpenPathWrapper");
+
try
{
_ = OpenPathAsync(sender, e);
}
catch (Exception ex)
{
+ activity?.RecordError(ex);
+ VsixTelemetry.TrackException(ex, new Dictionary
+ {
+ { "operation.name", "OpenPathWrapper" }
+ });
+
MessageBox.Show(
$@"
Fatal Error! Unable to invoke Super Clean!
@@ -60,14 +70,18 @@ Fatal Error! Unable to invoke Super Clean!
private static async Task OpenPathAsync(object sender, EventArgs e)
{
+ using var activity = VsixTelemetry.StartCommandActivity("SuperClean.OpenPathAsync");
+
var activeItem = await VS.Solutions.GetActiveItemAsync();
if (activeItem == null)
{
+ VsixTelemetry.LogInformation("No active item found");
return;
}
- switch (activeItem.Type)
+ activity?.SetTag("item.type", activeItem.Type.ToString());
+ switch (activeItem.Type)
{
case SolutionItemType.Solution:
try
@@ -78,9 +92,17 @@ private static async Task OpenPathAsync(object sender, EventArgs e)
{
throw new ApplicationException(errors);
}
+
+ VsixTelemetry.LogInformation("Solution super cleaned successfully");
}
catch (Exception ex)
{
+ activity?.RecordError(ex);
+ VsixTelemetry.TrackException(ex, new Dictionary
+ {
+ { "operation.name", "SuperCleanSolution" }
+ });
+
MessageBox.Show(
$@"
Unable to Super Clean solution
@@ -95,9 +117,16 @@ Unable to Super Clean solution
try
{
SuperCleanProject(activeItem);
+ VsixTelemetry.LogInformation("Project super cleaned successfully");
}
catch (Exception ex)
{
+ activity?.RecordError(ex);
+ VsixTelemetry.TrackException(ex, new Dictionary
+ {
+ { "operation.name", "SuperCleanProject" },
+ });
+
MessageBox.Show(
$@"
Unable to Super Clean project ${activeItem.Name}
@@ -112,28 +141,38 @@ Unable to Super Clean project ${activeItem.Name}
async Task<(bool, string)> SuperCleanSolution()
{
+ using var solutionActivity = VsixTelemetry.StartCommandActivity("SuperClean.SuperCleanSolution");
+
var success = true;
var errors = new StringBuilder();
+ var projectCount = 0;
foreach (var project in await VS.Solutions.GetAllProjectsAsync())
{
try
{
SuperCleanProject(project);
+ projectCount++;
}
catch (Exception ex)
{
errors.AppendLine(ex.Message);
success = false;
+ solutionActivity?.RecordError(ex);
}
}
+ solutionActivity?.SetTag("projects.cleaned", projectCount);
+ solutionActivity?.SetTag("success", success);
+
return (success, errors.ToString());
}
void SuperCleanProject(SolutionItem project)
{
- var projectPath =
+ using var projectActivity = VsixTelemetry.StartCommandActivity("SuperClean.SuperCleanProject");
+
+ var projectPath =
Path.GetDirectoryName(project.FullPath)
?? throw new InvalidOperationException();
@@ -143,11 +182,13 @@ void SuperCleanProject(SolutionItem project)
if (Directory.Exists(binPath))
{
Directory.Delete(binPath, true);
+ projectActivity?.SetTag("bin.deleted", true);
}
if (Directory.Exists(objPath))
{
Directory.Delete(objPath, true);
+ projectActivity?.SetTag("obj.deleted", true);
}
}
}
diff --git a/src/CodingWithCalvin.SuperClean/HoneycombConfig.cs b/src/CodingWithCalvin.SuperClean/HoneycombConfig.cs
new file mode 100644
index 0000000..99eb0fb
--- /dev/null
+++ b/src/CodingWithCalvin.SuperClean/HoneycombConfig.cs
@@ -0,0 +1,7 @@
+namespace CodingWithCalvin.SuperClean
+{
+ internal static class HoneycombConfig
+ {
+ public const string ApiKey = "PLACEHOLDER";
+ }
+}
diff --git a/src/CodingWithCalvin.SuperClean/SuperCleanPackage.cs b/src/CodingWithCalvin.SuperClean/SuperCleanPackage.cs
index a064cea..2328fe2 100644
--- a/src/CodingWithCalvin.SuperClean/SuperCleanPackage.cs
+++ b/src/CodingWithCalvin.SuperClean/SuperCleanPackage.cs
@@ -1,6 +1,7 @@
-using System;
+using System;
using System.Runtime.InteropServices;
using System.Threading;
+using CodingWithCalvin.Otel4Vsix;
using CodingWithCalvin.SuperClean.Commands;
using Microsoft.VisualStudio.Shell;
using Task = System.Threading.Tasks.Task;
@@ -20,7 +21,31 @@ IProgress progress
{
await JoinableTaskFactory.SwitchToMainThreadAsync(cancellationToken);
+ var builder = VsixTelemetry.Configure()
+ .WithServiceName(VsixInfo.DisplayName)
+ .WithServiceVersion(VsixInfo.Version)
+ .WithVisualStudioAttributes(this)
+ .WithEnvironmentAttributes();
+
+#if !DEBUG
+ builder
+ .WithOtlpHttp("https://api.honeycomb.io")
+ .WithHeader("x-honeycomb-team", HoneycombConfig.ApiKey);
+#endif
+
+ builder.Initialize();
+
SuperCleanCommand.Initialize(this);
}
+
+ protected override void Dispose(bool disposing)
+ {
+ if (disposing)
+ {
+ VsixTelemetry.Shutdown();
+ }
+
+ base.Dispose(disposing);
+ }
}
}