Skip to content

Add managed C# AppMap agent (under managed/)#34

Draft
evlawler wants to merge 1 commit into
masterfrom
claude/exciting-ritchie-ksbydi
Draft

Add managed C# AppMap agent (under managed/)#34
evlawler wants to merge 1 commit into
masterfrom
claude/exciting-ritchie-ksbydi

Conversation

@evlawler

@evlawler evlawler commented Jun 25, 2026

Copy link
Copy Markdown

What this is

This PR brings the fully managed C# AppMap agent into appmap-dotnet under a new managed/ subdirectory. It's a from-scratch port of the appmap-java architecture — a managed agent that rewrites methods at runtime via Harmony, rather than instrumenting IL from a C++ CLR-profiler plugin.

The motivation (vs. the existing C++ prototype): being fully managed makes it cross-platform (not Linux-only) and considerably easier to evolve, while emitting the same AppMap JSON (format v1.2) as appmap-java.

Layout

Everything lands under managed/the existing C++ prototype and its CI are untouched, so the two implementations sit side by side for comparison. (The agent's own CI workflows are at managed/.github/workflows/ and therefore do not auto-run in this repo.)

Project Role
managed/src/AppMap.Agent Config, recorder, event model, serializer, Harmony instrumentation, SQL + built-in hooks
managed/src/AppMap.Attributes [Labels] attribute for application code
managed/src/AppMap.StartupHook DOTNET_STARTUP_HOOKS entry point
managed/src/AppMap.AspNetCore HTTP server events, request + remote recording
managed/src/AppMap.SystemWeb The same for classic ASP.NET (.NET Framework)
managed/src/AppMap.Testing.{Xunit,NUnit} One AppMap per test
managed/test/AppMap.Agent.Tests Serializer / config / value-capture unit tests
managed/examples/{HelloAppMap,PetClinic} Smallest recorded app; ASP.NET Core + EF Core web app (HTTP + SQL)
managed/harness/ Records an unmodified real app (eShopOnWeb) and CLI-validates the maps

See managed/README.md for build/usage and managed/DESIGN.md for the design.

Status

Draft, opened for @dividedmind to review the approach. Imported as-is from the prototyping repo; happy to reshape placement, naming, or split it up based on feedback.

Imports the fully managed .NET AppMap agent (a from-scratch C# port of
appmap-java's architecture) developed in the Fun-with-Appmap-and-Claude
repo. Placed under managed/ alongside the existing C++ CLR-profiler
prototype so the two implementations can be compared without disturbing
the prototype or its CI.

Includes the agent (config, recorder, event model, serializer, Harmony
instrumentation, SQL/built-in hooks), startup hook, ASP.NET Core and
System.Web integrations, xUnit/NUnit test recorders, examples
(HelloAppMap, PetClinic), unit tests, and the eShopOnWeb harness.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01R1CtA2aMGjPuRYpfv2VcaX
@evlawler
evlawler requested a review from dividedmind June 25, 2026 13:48

evlawler commented Jul 3, 2026

Copy link
Copy Markdown
Author

@dividedmind — when you have a moment, could you take an early look at the approach here? Keeping it as a draft on purpose: this is a gut-check on direction, not a final PR.

The short version: a fully managed C# AppMap agent (Harmony-based runtime rewriting, porting the appmap-java architecture) landed under managed/, alongside the existing C++ prototype — nothing in the C++ path or its CI is touched. Motivation is cross-platform support and easier evolution vs. the CLR-profiler plugin, emitting the same AppMap JSON as appmap-java.

Mainly looking for feedback on placement/naming and whether this direction is worth pursuing. Happy to reshape or split it up. See the PR description, managed/README.md, and managed/DESIGN.md for details. Thanks!


Generated by Claude Code

@dividedmind dividedmind left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I really like the general idea of a managed recording agent – if it's indeed feasible. Couple of notes/nitpicks from a quick review:

  • The GitHub action workflows contain a lot of test code. Ideally, the test code should live in structured scripts so they could more easily be iterated on and run manually; github action should only have the minimal code to call out to them and to bind them together.
  • I'd prefer for this to live in a separate "orphan" branch (or a separate repository altogether) – with complete history if it's not too WIPpy – instead of being shoehorned into a subdirectory like this.
  • Using AppMap shouldn't require modifying production code (with the exception of labels – ideally they could be applied with no importing AppMap to the project, or if that's not feasible in a non-hacky idiomatic way, importing just a minimal annotation-only library – like appmap-java's com.appland.appmap.annotation – I see there's AppMap.Attributes here, good). The PetClinic example here explicitly pulls in UseAppMap in the server startup. Instead it should be automatically injected where needed (for example on building/running an AspNetCore server) when running with appmap configured (perhaps through a runner script – which seems to be missing here too? – or whatever is idiomatic). ZeroTouchWeb actually demonstrates this but is missing labels (and the runner script). Explicit UseAppMap should be de-emphasized (but still useful and documented, among others perhaps with the additional comment in the example, for more complicated cases that need more control). Runner script (or, eg. dotnet tool entry point – again, whatever's idiomatic) that sets the environment accordingly should be implemented; it's possible that it would not work correctly in more complicated pipelines so non-script way should also be documented, but it's an important ad-hoc easy entry point that should work for most users.
  • Similar concern for System.Web or tests – running with the runner or prepared environment should automatically inject and hook whatever's feasible (subject to configuration) – if not feasible, explicitly call out this gap. In particular especially the tests should be hooked and recorded unmodified. (The Attributes library could expose eg. an annotation to attach to tests to explicitly control/skip AppMap recording, but it should be entirely optional to use it.)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants