Skip to content
CAI
Software that uses CAICheck a score

appsignal/appsignal-elixir

72.1

Strong · 3 October 2026

6.7k

lines of production code

Elixir

with C

2

measurements over time

CAI band scale
CAI trend line
CAI lens gauges

What this system is

This system is the AppSignal Elixir agent, a library designed to provide comprehensive application performance monitoring and error tracking for Elixir applications. It instruments code via Telemetry integrations, decorators, and automatic logger backends to capture spans, metrics, and errors, while managing data transmission to the AppSignal backend. The system also includes diagnostic tools, check-in scheduling for heartbeats, and runtime probes to expose Erlang VM metrics.

How it got here

2016 — Span-based architecture migration

10 changes.

The project underwent a major architectural overhaul, shifting from a transaction-centric model to a modular, span-based tracing system with configurable, opt-in instrumentation for various libraries. This period involved significant refactoring of the C extension, the removal of legacy transaction registries, and the introduction of decorator-based APIs to support the new hierarchical tracing structure.

2017 — Diagnostic tools and test coverage expansion

9 changes.

This period focused on enhancing the library's diagnostic capabilities by introducing new Mix tasks for installation verification and system reporting. Concurrently, comprehensive test suites were added to cover core utilities, integration points, and the new diagnostic features, ensuring robust validation and reliability across the codebase.

2018–2021 — Probes system and error backend

10 changes.

This period focused on introducing a new minutely probe system for Erlang runtime metrics and an automatic error reporting backend via the Logger. Significant effort was also dedicated to expanding test coverage, including comprehensive tests for the new features and the creation of test helper modules for instrumentation verification.

2023–2024 — Logging and check-in integrations

4 changes.

This period focused on expanding AppSignal's core capabilities by introducing a native Erlang :logger handler for seamless log ingestion and a new check-in system for scheduling heartbeats and cron events. The work included implementing the underlying schedulers and transmission logic, replacing legacy HTTP clients with Finch, and adding comprehensive test coverage for both the logging backend and check-in mechanisms.

Features

Add AppSignal logger backend and Erlang :logger handler

Users can now integrate AppSignal with the Erlang/OTP :logger system. A new gen\_event backend (Appsignal.Logger.Backend) captures legacy Logger events, while a new :logger handler (Appsignal.Logger.Handler) registers with the modern Erlang logger to forward formatted log messages to AppSignal, enabling automatic log ingestion for applications using the standard logging infrastructure.

lib/appsignal/logger · high confidence

Automatic error reporting via new Logger backend

Appsignal now includes a new \Appsignal.Error.Backend\ that automatically attaches to the Erlang/OTP Logger. This backend intercepts unhandled process crashes and reports them to Appsignal, creating a new \background\_job\ span if no existing span is found, or attaching the error to an existing span if one is present. The feature includes configuration to enable/disable the backend, adds a \reported\_by\ tag to distinguish these errors, and explicitly ignores cowboy error reports and ignored processes.

lib/appsignal/error · high confidence

Introduce Credo and Dialyzer static analysis configurations

The project now includes \.credo.exs\ and \.dialyzer\_ignore.exs\ to enable static code analysis. Credo is configured with standard consistency, design, readability, and refactoring checks, while Dialyzer ignores are added to suppress warnings caused by type spec mismatches in the HTTPoison dependency.

(repo-wide) · high confidence

Introduce check-in scheduler with heartbeat and cron support

This change adds a new check-in system that allows users to schedule and transmit heartbeat and cron events to AppSignal. The implementation includes a scheduler that debounces transmissions, deduplicates redundant cron events, and handles graceful shutdowns to ensure pending events are sent. It also introduces a heartbeat mechanism that can run continuously via a GenServer, replacing the previous HTTP client (Hackney) with Finch for more efficient connection management.

_lib/appsignal/check\in · high confidence

Introduce minutely Erlang runtime metrics via new probe system

A new \Appsignal.Probes\ GenServer now executes registered probes every minute, starting with \Appsignal.Probes.ErlangProbe\ which reports Erlang VM metrics including IO, scheduler counts, process limits, memory usage, atom counts, run queue lengths, and scheduler utilization. The probe system handles probe registration, state management, and error logging to the integration logger, ensuring that metric collection failures do not crash the monitoring process.

lib/appsignal/probes · high confidence

New diagnostic and installation verification commands

AppSignal now provides three new Mix tasks to help users set up and troubleshoot the library. The \mix appsignal.diagnose\ task collects comprehensive system, configuration, and agent status information to aid in debugging, with an optional \--send-report\ flag to transmit the data to AppSignal support. The \mix appsignal.check\_install\ task verifies that the AppSignal NIF extension has loaded successfully, exiting with an error if it fails. Additionally, the \mix appsignal.demo\ task allows users to send sample performance and error data to verify their integration is working correctly.

lib/mix · high confidence

New instrumentation integrations and span-based tracing architecture

This release introduces dedicated instrumentation modules for Absinthe, Broadway, Ecto, Finch, HTTPoison, Oban, and Tesla, allowing AppSignal to automatically capture performance data and errors from these libraries via Telemetry. Under the hood, the library has shifted from a Transaction-centric model to a Span-based architecture, introducing the \Appsignal.Span\ and \Appsignal.Tracer\ modules to manage hierarchical tracing, while also adding a new \Appsignal.Demo\ module for testing instrumentation flows.

lib/appsignal · high confidence

Removals

Removal of the legacy TransactionRegistry module

The \Appsignal.TransactionRegistry\ module, which previously managed transaction handles in an ETS table and monitored originating processes, has been removed from the codebase. This change eliminates the internal registry logic that tracked transactions and cleaned up entries upon process termination, indicating a shift in how transaction lifecycle and process monitoring are handled within the library.

lib/appsignal/transaction · high confidence

Behavioural changes

Introduce decorator-based instrumentation and helper modules

Users can now instrument code using new Elixir decorators (\@instrument\, \@transaction\, \@transaction\_event\, \@channel\_action\) defined in \Appsignal.Instrumentation.Decorators\, which wrap function execution to create spans or root transactions. A new \Appsignal.Instrumentation.Helpers\ module provides convenience delegates for manual instrumentation, including a deprecated \instrument/4\ function that redirects to the new API. This change shifts the instrumentation approach from previous macro-based or manual methods to a declarative decorator style.

lib/appsignal/instrumentation · high confidence

Major architecture overhaul with configurable instrumentation and new system probes

The library has been significantly refactored to support a modular, opt-in instrumentation model. The application startup now conditionally attaches integrations for Ecto, Finch, Oban, Tesla, Absinthe, and Broadway based on configuration flags, replacing the previous automatic or transaction-centric approach. The core supervision tree has shifted from managing a TransactionRegistry to hosting new components: Tracer, Monitor, Probes, and a CheckIn Scheduler. Additionally, the system now registers default Erlang system probes to expose scheduler utilization metrics, and the public API for metrics like \set\_gauge\ and \increment\_counter\ has been updated to accept optional tags.

lib · high confidence

Migrate to Elixir Config and inject test fakes

The configuration system has been updated to use the modern \import Config\ syntax, replacing the deprecated \Mix.Config\. In test environments (\:bench\, \:test\, \:test\_no\_nif\), the application now automatically configures a comprehensive set of fake implementations (such as \FakeSystem\, \FakeNif\, \FakeTransmitter\, and \FakeScheduler\) to isolate the test suite from external services and native code, while also defining specific test credentials and a dedicated test repository.

config · high confidence

New agent diagnostics report structure

The agent diagnostics output now includes a dedicated 'Agent tests' section that verifies the agent has started, checks the process user and group IDs, validates the configuration, confirms the logger is running, inspects the working directory permissions and ownership, and tests lock path writability. This complements the existing 'Extension tests' for configuration validity, providing a more comprehensive view of the agent's runtime state during diagnosis.

lib/appsignal/diagnose · high confidence

Redesigned argument sanitization and data encoding for safer telemetry

The library introduces new internal utilities to standardize how data is prepared for transmission. Appsignal.Utils.ArgumentCleaner now sanitizes function arguments by redacting sensitive values (such as binary strings and bitstrings) while preserving structural information (like map keys and tuple sizes) to aid debugging without exposing secrets. Appsignal.Utils.DataEncoder handles the serialization of complex Elixir terms (maps, structs, lists, and large integers) into a format suitable for the backend, ensuring improper lists and big integers are handled correctly. Additionally, Appsignal.Utils.MapFilter provides robust parameter filtering compatible with both Phoenix 1.18+ and older versions, allowing users to configure which request parameters are discarded or kept before reporting.

lib/appsignal/utils · high confidence

Refactor C extension to use reference-based Span API and new agent header

The C extension (c\_src/appsignal\_extension.c) has been refactored to align with the new AppSignal agent API. The include path has changed from appsignal\_extension.h to appsignal.h, and the internal resource management has shifted from a single transaction-based model to separate data and span resource types. This enables a reference-based child Span API, allowing spans to be created and managed independently via new NIFs like \_create\_child\_span and \_close\_span, rather than being tightly coupled to the transaction lifecycle. Additionally, the extension now exposes environment variable management functions (\_env\_put, \_env\_get, etc.) and supports setting gauges and counters on data resources.

_c\src · high confidence

Update bundled CA certificates

The bundled CA certificate file (priv/cacert.pem) has been updated to the version from Mozilla as of December 2, 2025. This ensures that SSL/TLS connections made by the application trust the latest set of public Certificate Authorities, maintaining secure connectivity with external services.

priv · high confidence

Test coverage

Add Registry and Transaction Match benchmarks; Added test coverage for AppSignal Elixir integration components; Added test coverage for AppSignal check-in functionality; Added test coverage for argument cleaning, data encoding, map filtering, and API key validation; Added test fixture for Phoenix template render instrumentation; Added test support fakes for Appsignal diagnostics, NIFs, and metrics; Added test support infrastructure and fakes; Added tests for Appsignal.Error.Backend; Added tests for ErlangProbe metrics and Probes registry behavior; Added tests for Mix helper installation and system detection; Added tests for diagnose paths and report transmission; Added tests for the Appsignal Logger backend and Erlang :logger handler; Added tests for the new check\_install and diagnose mix tasks; New test helper modules for instrumentation verification; Removal of legacy Appsignal test suite; Updated diagnose integration test submodule.

Dependencies

AppSignal Elixir agent upgraded to v2.18.1 with Elixir 1.9+ requirement

The AppSignal Elixir package has been updated to version 2.18.1, raising the minimum supported Elixir version to 1.9. This release replaces the previous JSON-based agent configuration with a new \agent.exs\ file and bundles the CA certificate (\priv/cacert.pem\) directly in the package. The dependency management has been significantly refactored to use version-specific constraints for libraries like Finch, Telemetry, and HTTPoison based on the running Elixir and OTP versions, ensuring compatibility across the supported matrix. Additionally, the compilation task now explicitly clears AppSignal environment overrides before installation to prevent test fake modules from interfering with the extension setup.

(dependencies) · high confidence

Housekeeping

Changesets directory initialization

The .changesets directory has been initialized with a .gitkeep file to support the changesets tooling for tracking upcoming changes.

.changesets · high confidence

Written by watchdog.canine.dev from the codebase's own history, inside the signed delivery this page is composed from.

How this codebase got here

Score

  • CAI 70 → 72 (+1.7)
  • Rubric changed (rubric-2026.09.15 → rubric-2026.10.1) — scores are not directly comparable.

Lenses

  • Code Health 97 → 97 (+0.1)
  • Architecture 96 → 85 (-10.5)
  • Maturity 65 → 66 (+0.9)
  • Readiness 76 → 78 (+1.7)
  • Security 65 → 72 (+6.9)

Resolved (2)

  • Duplicated block (21–27 lines × 2) (lib/appsignal/absinthe.ex)
  • Off-boarding risk: anonymized user #1

New (4)

  • Documentation: no contributor guidance (README.md)
  • Duplicated block (23–29 lines × 3) (lib/appsignal/absinthe.ex)
  • Off-boarding risk: anonymized user #1
  • Projects may be oversized for their cohesion

Changes since last survey

  • 13 commits — 13 feature/other, 0 fixes

By area

  • (root) — 8 commits
  • (repo) — 2 commits
  • .changesets/broadway-message-payload-are-span-payloads.md — 1 commit
  • lib/appsignal — 1 commit
  • test/appsignal — 1 commit

Notable commits

  • change: Add Broadway instrumentation
  • change: Broadway message payloads are span payloads (#1063)
  • change: Merge pull request #1057 from appsignal/update-agent/0.37.2
  • change: Merge pull request #1058 from appsignal/add-broadway-instrumentation
  • change: Merge pull request #1059 from appsignal/read-registry-through-tracer
  • change: Publish package v2.17.6
  • change: Publish package v2.17.7
  • change: Publish package v2.18.0
  • change: Publish package v2.18.1
  • change: Test the tracer registry through its public API
  • change: Update agent to version 0.37.3 (#1060)
  • change: Update agent to version 0.37.4 (#1061)
  • change: Update the README file (#1062)

Written by watchdog.canine.dev from the codebase's own history, inside the signed delivery this page is composed from.

Survey your own repository

appsignal/appsignal-elixir was measured the same way every project in this corpus was: the same rubric, at a pinned commit, with the result published in full. Point a surveyor at a repository you know and see whether you agree with it.

About this page

  • The score is its most recent published measurement, taken on 3 October 2026 at a pinned commit. It is not a live figure and does not change until the project is measured again.
  • Measured at commit bbb4904e37d4e47c19b4f4d6d1c023b38425aca8 — the exact code this score is about.
  • Scored under rubric-2026.10.1 — the same rubric and the same method as every other entry in this index.
  • Measured by watchdog.canine.dev using codehealth-analyzer preprod-24c657e50118.