I previously wrote a post called "Get the damned version". This post is tentatively entitled "There Is More Than One Way To Get The Damned Version" and speaks about the plethora of applications and modules to get versions. Brace yourself!
So, apparently I'm not the only one who hates how you cannot distinctively get the version of a specific module. We have various trickeries such as loading the module and printing it, trying to load an unknown - yet hopefully - non-existent advanced version and failing thus showing the version and a few other such odd possibilities... and then there are the modules and applications.
While use.perl.org proves yet again to suck (and this time by not being able to continuously supply the simple CPAN module uploads RSS stream), I've gone to the original stream (which shows every single module upload as an RSS item), I noticed that a new module and application surfaced called App::Mver.
I reckon this is time to recap:
Module::Extract::VERSION (by brian d. foy): as with any project that has brian's name on it, it's clean, simple and strict. It can return the version, the filename and even the line number of where the $VERSION variable was found, amongst other things. Under the hood it is basically the code taken from mldistwatch, but refactored (and most likely cleaned up). It uses ExtUtils::MakeMaker and runs an eval.
Hidden benefits: it can find versions that were declared on two lines (our\n$VERSION) and it doesn't get confused by POD syntax. It being almost the exact same code that runs on PAUSE (and being authored by brian) means it's stable as F&$K. You can pretty much count on this.
Disadvantage: it is something to be used only in a module, it does not have an application. That means that any added functionality is needed to be written by you.
- Module::Which (by Adriano Ferreira): another module from a deservingly respected author. It exports a single function (using @EXPORT instead of @EXPORT_OK). It uses ExtUtils::MakeMaker as well, specifically the parse_version method. Clean, slick. It has some wrappers for returning the information back in a hash as well (giving named keys for the data) which is nice. Seems like a few other features were tried and so far hasn't materialized (or were thrown back into design) by the commented subroutines in the source.
Benefits: the actual command (named which) supports multiple modules and perl itself. Adriano also took into account the amount you have to normally write without using this module and showed it in the POD.
Disadvantages: while it is true this module allows you to write less in the command line, it is only valid if you write your own application wrapper around it. If not, you'll need to write practically the same amount of letters as you would in any other case.
- Module::InstalledVersion (Kirrily "Skud" Robert): this module takes pretty much the same approach as others. It went a step beyond (?) and just copied the ExtUtils::MakeMaker version regex and matches against it.
Benefits: returns both the version and the directory. It's a simple module and that is probably why the last release was in 2001.
Disadvantages: it assumes the EU::MM regex will never change (specifically since the version of EU::MM it took the regex from), doesn't allow multiple, doesn't return additional information and has no CLI application.
- V (by Abe Timmerman): except winning the title of shortest (and best) module name for this type of thing, Abe's V is the shortest way to get a module's name strictly via a module - thanks to the aforementioned title.
Benefits: supports multiple modules, short, clean, nice. Doesn't suck to run as a command line utility.
Disadvantages: copied some stuff from Module::Info and EU::MM_Unix and that is bad in case of updates to those modules. Also, as all mentioned above, it is missing a CLI app but thanks to clever design, it's not that bad!
- App::whichpm (by Jozef Kutej): finally a proper application. It is even properly separated into a module and frontend CLI application. It was released slightly (a month) before Module::Version (which is covered last) and provides a beginner-friendly way of getting a module version. It implements its own find subroutine to find the module. It uses it (in eval) and then eval's the VERSION method of it. Although interesting, it is a behavior Module::Version has already deprecated.
Benefits: few dependencies, which is nice. A CLI application which is exactly what all the above were missing.
Disadvantages: this doesn't seem like it was written to really get a module's version, but rather the path to the module. The version retrieval seems more like a side-effect and that explains a lack of a variety of options for the application.
- App::Mver (by KSURI): this module was originally released only yesterday. It is not just a module, but also an application. So far it sports the shortest name for an application to retrieve module versions. It does exactly the same thing as App::whichpm, except it doesn't try to find the path. The rest of the code is eval upon eval.
Benefits: CLI application which is nice.
Disadvantages: kind of pointless, now that other applications exist, especially when some actually run the exact same code as you are, literally. This module/app also doesn't provide any options, the CLI isn't documented and there is no --help. Also, mver seems like the name for an application wrapper or a better version of the Unix mv command, which is why I'll probably never install such an application - to avoid messing with names. They should try to be unique, IMHO.
- Module::Version (by Sawyer X): obviously my favorite choice, because I wrote it to suit what I wanted and felt was needed. Unlike the aforementioned projects, Module::Version attempts to be as clear and yet as feature-full as possible for users. Not hardcore Perl programmers but users. Seasonal Perl programmers, beginners, sysadmins, and random users. Module::Version has many features, supports multiple usages and in light of it, I personally cannot fathom why App::mver was written (except, perhaps, for short-sight of the author). I'm not a narcissist person (at least I hope I'm not), but I reckon the benefits speak for themselves.
Benefits: CLI application, relatively short app name (mversion), clearly separated to Module::Version which provides get_version (using @EXPORT_OK only) and Module::Version::App which is the logic behind mversion command line. It supports multiple module names, verbose syntax (name and version, not just the version), reading from an input file, warnings on missing (or modules it was unable to parse), quiet mode to suppress those warnings, non-evaling on dev versions option (returning 0.01_1 instead of 0.01, which is the default), and even including additional multiple directories like perl has with the -Ilib option. It also features full documentation and clean, concise code. The main function is literally 4 lines (not including sub declaration and closing brace). It honestly doesn't eval the result but uses ExtUtils::MakeMaker function to find the module file and parse the version.
Disadvantages: it doesn't support local::lib yet, but it will! :)