Overview
Metrix++ is the
platform to collect and analyse code metrics.
- It has got plugin based architecture, so it is easy to
add support for new languages and/or define new metrics
and/or create new pre- and post-processing tools.
- Every metric has got 'turn-on' and other configuration
options.
- There is no predefined thresholds for metrics or rules.
You can choose and configure any limit you want.
- It scales well to big code bases. For example initial
parsing of about 10000 files takes 2-3 minutes on average
PC, and ONLY 10-20 seconds for iterative re-run. Reporting
summary results and exceeded limits is less than 1 - 10
seconds.
- It can compare results for 2 code snapshots (collections)
and differentiate added regions (classes, functions, etc.),
modified regions and unchanged regions.
- As a result, easy deployment is guaranteed into legacy
software, helping you to deal with legacy code effiently -
either enforce 'leave it not worse than it was before' rule
or motivate re-factoring.
Standard Plugins
The distributive includes a set of standard plugins:
Code parsers
- C/C++ parser
recognises definition of namespaces, definition of
classes/structs (including enclosed in functions),
templates and definition of functions/operators
- C# parser
recognises definition of namespaces, definition of
classes/structs (including enclosed in functions),
interfaces, generics, definition of
functions/operators
- Java parser
recognises definition of classes (including local in
functions), interfaces, generics and functions
Metrics
- cyclomatic
complexity (by McCabe) per function [supports C/C++, C#, Java
languages]
- processing
errors per file [supports any file
type]
- processing time
per file [supports any file
type]
Analysis tools
- export.py -
exporter to xml, python or plain text of detailed
information per file and/or aggregated information per
file or directory [aggregated data includes sum, maximum, minimum, average within a subset
of selected files or directories]
- limit.py - a
tool to report regions exceeding speified thresholds,
which are configurable (output is plain text with
metadata compatible with gcc compiler warning
messages)
- info.py - a
tool to show file metadata, such as properties,
namespaces and fields recorded
Download & Installation
For the installation of the Metrix++ download
the archive with the latest
stable version and unpack it to some folder.
Corresponding checkout from the version control system:
> svn checkout https://metrixplusplus.svn.sourceforge.net/svnroot/metrixplusplus/releases/<version>
Alternatively, there is an option to download
tarball file with the latest
development version of the tool or checkout this version
of source
code from the version conrol system:
> svn checkout https://metrixplusplus.svn.sourceforge.net/svnroot/metrixplusplus/mainline/
Prerequisites:
Python Runtime Environment (version 2.7.0 or later, version
3.0 has not been tested)
License:
This program is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public
License as published by the Free Software Foundation; version 3
of the License.
This program is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied
warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
PURPOSE. See the GNU General Public License for more
details.
You should have received a copy of the GNU General Public
License along with the Metriix++; if not, contact Project
Administrator and write to the Free Software Foundation,
Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301
USA.
Documentation
Tools are self-descriptive and have got comprehensive
context help. Type in the command line: python
<tool-name>.py --help
Known Limitations
Check 'doc/limitations.txt' file distributed with the tool
or browse for recent version online.
Basic Workflow
Assuming that you opened a terminal and your current working
directory is in the root folder of the tool installed.
I. Start with running a collector tool,
enabling a collection of cyclomatic complexity:
> python collect.py --std.code.complexity.on -- /path/to/your/project ../../path/to/some/other/project
It will generate a database file in working directory with
default name. In order to change the name or location, use
corresponding command line option. Depending on a size of code
base, collection may take seconds or minutes, but it is very
fast in general. In order to achive the highest performance (~
to calculation of crc32) for iterative re-scans, point out to
the dabase file collected for the previous code revision:
> python collect.py --std.code.complexity.on --general.db-file-prev=metrixpp-prev.db --
/path/to/your/project
Paths are optional. If you do not specify a path, it will
scan files in the current working directory. Check other
available options for the tool by executing:
> python collect.py --help
II. Secondly, export data using export
tool.
> python export.py --
<export>
<data>
<info path="" id="1" />
<file-data />
<subfiles>
</subfiles>
<subdirs>
<subdir>path</subdir>
</subdirs>
<aggregated-data>
<std.code.complexity>
<cyclomatic max="2" total="14.0" avg="0.168674698795" min="0" />
</std.code.complexity>
</aggregated-data>
</data>
</export>
By default, it exports all aggregated data for all files
scanned in xml format. It is possible to re-configure output
format to python or plain text. In order to narrow the scope,
specify a path to directory or a file. In order to export only
subset of metrics, specify them as well.
> python export.py --general.format=python --general.namespaces=std.code.complexity --
/path/to/your/project/subdir
<export>
...
</export>
If you have got results collected for previous version,
point out to the file using the corresponding option and the
tool will add diff data.
> python export.py --general.namespaces=std.code.complexity --general.db-file-prev=metrixpp-prev.db --
<export>
<data>
<info path="" id="1" />
<file-data />
<subfiles>
</subfiles>
<subdirs>
<subdir>path</subdir>
</subdirs>
<aggregated-data>
<std.code.complexity>
<cyclomatic max="2" total="14.0" avg="0.168674698795" min="0">
<__diff__ max="0" total="0.0" avg="0.0" min="0" />
</cyclomatic>
</std.code.complexity>
</aggregated-data>
</data>
</export>
Check other available options for the tool by executing:
> python export.py --help
III. Finally, identify code regions which
exceed a specified limit, applying it to all scanned files:
> python limit.py --general.max-limit=std.code.complexity:cyclomatic:7 --
/path/to/your/project/ui/notifications.cpp:72: warning: Metric 'std.code.complexity/cyclomatic' for
region 'doFont' exceeds the limit.
Metric name : std.code.complexity/cyclomatic
Region name : doFont
Metric value : 10
Modified : None
Change trend : None
Limit : 7
/path/to/your/project/ui/notifications.cpp:144: warning: Metric 'std.code.complexity/cyclomatic' for
region 'doStyle' exceeds the limit.
Metric name : std.code.complexity/cyclomatic
Region name : doStyle
Metric value : 9
Modified : None
Change trend : None
Limit : 7
You can limit the scope of analysis by defining paths to
directories or files.If you have got results collected for
previous version, point out to the file using the corresponding
option and the tool will notify about change status:
> python limit.py --general.max-limit=std.code.complexity:cyclomatic:7
--general.db-file-prev=metrixpp-prev.db --
/path/to/your/project/ui/notifications.cpp:72: warning: Metric 'std.code.complexity/cyclomatic' for
region 'doFont' exceeds the limit.
Metric name : std.code.complexity/cyclomatic
Region name : doFont
Metric value : 10
Modified : True
Change trend : 0
Limit : 7
/path/to/your/project/ui/notifications.cpp:144: warning: Metric 'std.code.complexity/cyclomatic' for
region 'doStyle' exceeds the limit.
Metric name : std.code.complexity/cyclomatic
Region name : doStyle
Metric value : 9
Modified : True
Change trend : +1
Limit : 7
Another useful option for this tool helps you to deal with legacy code. It is not
unusual if you have got enormous number of warnings enabling
new thresholds for the code designed in the past, which has not
be profiled/targeted to specific metric limits. By default the
tool warns about all code regions, ignoring their change
status. You can reconfigure it to one of the following:
- warn only about new
code regions (functions, classes):
> python limit.py --general.max-limit=std.code.complexity:cyclomatic:7
--general.db-file-prev=metrixpp-prev.db --general.warn=new --
- warn about new code
regions and modifed regions
regressing the metric (enforces the
rule 'leave not worse than it was before'):
> python limit.py --general.max-limit=std.code.complexity:cyclomatic:7
--general.db-file-prev=metrixpp-prev.db --general.warn=trend --
/path/to/your/project/ui/notifications.cpp:144: warning: Metric 'std.code.complexity/cyclomatic' for
region 'doStyle' exceeds the limit.
Metric name : std.code.complexity/cyclomatic
Region name : doStyle
Metric value : 9
Modified : True
Change trend : +1
Limit : 7
- warn about new and
all modified regions
(motivates for refactoring of legacy code):
> python limit.py --general.max-limit=std.code.complexity:cyclomatic:7
--general.db-file-prev=metrixpp-prev.db --general.warn=touched --
/path/to/your/project/ui/notifications.cpp:72: warning: Metric 'std.code.complexity/cyclomatic' for
region 'doFont' exceeds the limit.
Metric name : std.code.complexity/cyclomatic
Region name : doFont
Metric value : 10
Modified : True
Change trend : 0
Limit : 7
/path/to/your/project/ui/notifications.cpp:144: warning: Metric 'std.code.complexity/cyclomatic' for
region 'doStyle' exceeds the limit.
Metric name : std.code.complexity/cyclomatic
Region name : doStyle
Metric value : 9
Modified : True
Change trend : +1
Limit : 7
Check other available options for the tool by executing:
> python limit.py --help
Bug Report & Feature Request
Any types of enquiries are welcomed by e-mail to project
administrator.
Create Plugin
Please, consider to join the project and contribute to the development
of the engine or include you
plugins into the standard set of plugins distributed
together with this tool. Contact project
administrator by e-mail.
New Metric
Unfortunately, there is no rich documentation at this stage.
Briefly, any new plugin starts with creating 2 new files: 'ini'
and 'py'. You can copy from other avaialble (for example, ini
and py
files for the standard complexity plugin) and impelement the
logic related to the new metric.
New Analysis Tool
Unfortunately, there is no rich documentation at this stage.
Briefly, database API (class Loader implemented in 'core.db.loader')
is a starting point for any new post-analysis tool. There are 2
standard tools (export.py
and limit.py)
available which use this API.
New Language Support
Unfortunately, there is no rich documentation at this stage.
Briefly:
- a plugin is registered in the same way as a plugin for
new metric
- it subscribes to directory reader plugin
- parses a file in a callback, called by directory
reader
- parser needs to identify markers (like comments, strings,
preprocessor) and regions (like functions, classes, etc.)
and tell about this to file data object passed as an
argument for the callback.
Parser for C/C++ language can serve as an
example. There useful options and tools are avaialble for
trobuleshooting purposes during development:
- debug.py tool is
helpful troubleshooting tool. In mode 'dumphtml' it
generates html code showing code highlightings
- --general.nest-regions for
export tool forces exporting of code structure in tree
format. It can be helpful for analysis of parser's
internals
- --general.log-level=GENERAL.LOG_LEVEL
for any tool is helpful to trace execution
Finally, if there are any questions or enquires, please,
feel free to contact project
administrator by e-mail.
Source Code Repository
Source code is in the Subversion repository (browse
online) used by the project. Corresponding checkout command
is the following:
> svn checkout https://metrixplusplus.svn.sourceforge.net/svnroot/metrixplusplus/mainline/
|