argon: Measure your code's complexity

[ development, static-analysis ] [ Propose Tags ] [ Report a vulnerability ]

Argon performs static analysis on your code in order to compute cyclomatic complexity. It is a quantitative measure of the number of linearly indipendent paths through the code.

The intended usage is through Argon's executable, which accepts a list of files or directories to analyze. The data can be optionally exported to JSON.


[Skip to Readme]

Modules

[Last Documentation]

  • Argon

Downloads

Maintainer's Corner

Package maintainers

For package maintainers and hackage trustees

Candidates

  • No Candidates
Versions [RSS] 0.1.0.0, 0.2.0.0, 0.3.0.0, 0.3.1.0, 0.3.1.1, 0.3.1.2, 0.3.2.0, 0.4.0.0, 0.4.1.0, 0.4.2.0
Change log CHANGELOG.md
Dependencies aeson, ansi-terminal, argon, base (>=4.7 && <5), bytestring, Cabal, containers, directory, dirstream, docopt (>=0.7), filepath, ghc, ghc-boot, ghc-paths, ghc-syb-utils, lens-simple, pipes (>=4.1), pipes-bytestring, pipes-group, pipes-safe (>=2.2), syb, system-filepath [details]
Tested with ghc >=8.0.2 && <9
License ISC
Copyright 2015 Michele Lacchia
Author Michele Lacchia
Maintainer michelelacchia@gmail.com
Category Development, Static Analysis
Home page http://github.com/rubik/argon
Bug tracker http://github.com/rubik/argon/issues
Source repo head: git clone https://github.com/rubik/argon
Uploaded by rubik at 2024-10-28T17:07:26Z
Distributions
Executables argon
Downloads 7295 total (36 in the last 30 days)
Rating 2.0 (votes: 1) [estimated by Bayesian average]
Your Rating
  • λ
  • λ
  • λ
Status Docs not available [build log]
All reported builds failed as of 2024-10-28 [all 2 reports]

Readme for argon-0.4.2.0

[back to package description]

Argon

Tests Code coverage License Version

Argon measures your code's cyclomatic complexity.

Argon screenshot


Installing

Simple as stack install argon or cabal install argon. Note: if you are using Stack and your resolver if too old, you might have to add some packages to your stack.yaml file.

GHC compatibility

Argon is compatible with GHC version 8.0.2 and above. In the releases page you can find binaries for older versions of argon which support GHC versions 7.8 and 7.10.

About the complexity being measured

argon will compute the cyclomatic complexity of Haskell functions, which is the number of decisions in a block of code plus 1. For instance the following function:

func n = case n of
           2 -> 3
           4 -> 6
           _ -> 42

has a cyclomatic complexity of 3.

The boolean operators && and || also affect the this number. For instance the following function:

g n = n < 68 && n `mod` 3 == 2 && n > 49

has a cyclomatic complexity of 3.

As a last example, the following function:

func n = case n of
           2 -> 3
           4 -> 6
           _ -> if 0 < n
                then 7
                else 8

has a cyclomatic complexity of 5.

Cyclomatic complexity provides a very shallow metric of code complexity: a high cyclomatic complexity number does not necessarily mean that the function is complex, and conversely, a low number does not necessarily indicate that the function is simple. However, this number it can be useful for highlighting potential maintainability issues.

Running

The Argon executable expects a list of file paths (files or directories):

$ argon --no-color --min 2 src
src/Argon/Types.hs
    61:5 toJSON - 2
src/Argon/Visitor.hs
    55:1 visitExp - 5
    62:1 visitOp - 4
    28:11 visit - 2
    35:1 getFuncName - 2
src/Argon/Parser.hs
    55:1 parseModuleWithCpp - 3
    88:1 customLogAction - 3
    35:1 analyze - 2
    39:9 analysis - 2
src/Argon/Formatters.hs
    61:1 formatResult - 3
    42:1 coloredFunc - 2
    43:11 color - 2
src/Argon/Results.hs
    35:1 export - 3
    28:1 filterResults - 2
src/Argon/Loc.hs
    18:11 toRealSrcLoc - 2

For every file, Argon sorts results with the following criteria (and in this order):

  1. complexity (descending)
  2. line number (ascending)
  3. alphabetically

When colors are enabled (default), Argon computes a rank associated with the complexity score:

Complexity Rank
0..5 A
5..10 B
above 10 C

JSON

Results can also be exported to JSON:

$ argon --json --min 2 src
[
  { "blocks": [ ], "path": "src/Argon.hs", "type": "result" },
  {
    "blocks": [{ "complexity": 2, "name": "toJSON", "lineno": 61, "col": 5 }],
    "path": "src/Argon/Types.hs",
    "type": "result"
  },
  {
    "blocks": [
      { "complexity": 5, "name": "visitExp", "lineno": 55, "col": 1 },
      { "complexity": 4, "name": "visitOp", "lineno": 62, "col": 1 },
      { "complexity": 2, "name": "visit", "lineno": 28, "col": 11 },
      { "complexity": 2, "name": "getFuncName", "lineno": 35, "col": 1 }
    ],
    "path": "src/Argon/Visitor.hs",
    "type": "result"
  },
  {
    "blocks": [
      { "complexity": 3, "name": "parseModuleWithCpp", "lineno": 55, "col": 1 },
      { "complexity": 3, "name": "customLogAction", "lineno": 88, "col": 1 },
      { "complexity": 2, "name": "analyze", "lineno": 35, "col": 1 },
      { "complexity": 2, "name": "analysis", "lineno": 39, "col": 9 }
    ],
    "path": "src/Argon/Parser.hs",
    "type": "result"
  },
  {
    "blocks": [
      { "complexity": 3, "name": "formatResult", "lineno": 61, "col": 1 },
      { "complexity": 2, "name": "coloredFunc", "lineno": 42, "col": 1 },
      { "complexity": 2, "name": "color", "lineno": 43, "col": 11 }
    ],
    "path": "src/Argon/Formatters.hs",
    "type": "result"
  },
  {
    "blocks": [
      { "complexity": 3, "name": "export", "lineno": 35, "col": 1 },
      { "complexity": 2, "name": "filterResults", "lineno": 28, "col": 1 }
    ],
    "path": "src/Argon/Results.hs",
    "type": "result"
  },
  {
    "blocks": [{ "complexity": 2, "name": "toRealSrcLoc", "lineno": 18, "col": 11 }],
    "path": "src/Argon/Loc.hs",
    "type": "result"
  },
  { "blocks": [ ], "path": "src/Argon/Preprocess.hs", "type": "result" }
]