And I didn't begin to feel mastery with Maven until I started writing plug-ins. If you really want to understand your tool, then try extending it. I've never had issues with Maven builds missing files, etc. and I'm not really sure how that happens. On the other hand, the fact that the project structure is almost always the same from project to project lets me successfully dive into projects I've never touched.
But Maven can be complex, especially if you're not careful to segment your project into sub-projects and modules. There are parts that are best learned by working with someone who's already mastered the build system. In any case, I think make/autoconf are harder to grasp than Maven, and I've never hated it the way I do when I'm programming in XML (Ant).
Trust me, us maven haters understand declarative programming just fine. There is no impedence mismatch. Maven the build tool is simply an inferior solution with several superior alternatives. After discovering Buildr, I've never wanted to go back to Maven, and I'm willing to trust that Gradle (Groovy), Leiningen (Clojure), and SBT (Scala), are all also superior to Maven while integrating well with Maven's dependency system.
Except that they don't. They can consume it, but they can't produce it. Or do they make pom files now? Or do you not care about pom files because you'll never publish your source?
On the other hand, unfortunately it doesn't scale to the low end.
I had a task just to transform a jar file. With Maven it took hours of scratching my head, finding the assembly plug-in, having Maven download 100Mb of stuff; all to do what would take a minutes of development time and executation time total to do in Python or Perl.
That makes you scream inside.
I've written a few maven plugins that are just jython wrappers that import a few flags into the jython script (like the build directory) and then execute them. I've even written a generic python plugin that executes a script at a given path and imports any declared maven variables into it.
Sometimes it feels wrong, I know, but it's worth it.
I also wrote a new site plugin for myself that diffs between versions and throws all that up on a site for a auto changelog thing. It's useful for those rare "What the fuck did you do to the code in this release" occasions.
With maven, I pretty much need a multi-module project for even simple things (mostly because I code Java using eclipse and eclipse needs a workspace above my projects generally speaking) and doing that is a lot of incantation to get up and running.
Maven is perfectly fine for small projects, but a totally waste of time at the large scale.
If your project is a few hundred classes, that use some-popular-web-framework and some-orm, and get packaged into a single WAR file, then Maven is simple, it works and it lets you avoid thinking about the build.
If your project is thousands of classes using a variety of technologies (Corba, JMS, Web, etc) with layers of dependencies, then Maven should help, since it should allow you to manage all those technologies through a similar process, but it just collapses under the strain.
The bits that tend to get in the way (some of this is probably specific to Maven 2, but I got burnt enough back then that I'm not willing to revisit it all and see what happens with Maven 3)
Despite multi-module being the right way to solve things (both the Maven team's opinion and mine) it works really badly. If you want to compile & test your whole project each time, then you're all good, but if you want to cut your build process down and just recompile the modules that you're working on, you're going to lose most of that time saving in trying to wrangle Maven into doing things properly. The main issue is the dependency management is all built around the idea that you only ever depend on jar files in a repository. So, in a multi-module project where you actually want to depend on "the source code sitting in a sibling directory", things go wrong.
Despite Maven's theories about having a standardised project model, too much ends up being left to the plugin authors. If you're using more esoteric plugins (e.g. the Corba IDLc plugins) then you'll get caught out by issues that the plugin authors didn't think of. Plugin-X looks for a resource file on the classpath (but only the main classpath, not the test one), Plugin Y looks for its resource file on the file system, Plugin Z will look for a file on the classpath, but crashes if that file is inside a jar, but you need to reference a jar because the file is coming from another module in your multi-module project, and you can only express dependencies on jar files. So to work around that you add a step in your build to unpack the jar into a temporary location and add that location to the classpath. And you though maven wasn't procedural.
One artifact per module is a nice idea thought up by people who assumed that their experiences were diverse enough to solve everyone else's problems. Unsurprisingly they're wrong. But to keep maven happy you split your project into dozens of modules each with 1 artifact. But that makes your build even slower, and creates even more issues with managing the dependencies between modules. And even if you do that, you still end up hacking your pom to create more than 1 artifact because sometimes you really need to.
Handling test support code in a multi-module project is painful. Well written tests need supporting code. But that is neither "test" code (because test code is not exported out of your module) nor "main" code (because you don't want to ship it). So either, you create extra modules to handle testing. In the worst case, you need to split each module into 3 - the main code, the test support code, and the actually tests.
So, in summary, the pain you're feeling with a small project, is just multiplied exponentially as your project grows.
If they just right some apporachable documentation, it would be so much better.
People who accept this are (the majority of) happy Maven users. People who fight Maven write angry blog posts.
When you are building a product (e.g. an installer, some documentation, a website ... etc.) with the build tool, what you create is an artifact, that once built you can treat independently of its dependencies. A module is library code, and when you depend on it you implicitly depend on its dependencies as well.
Build languages/dsls are a complete intellectual cul-de-sac. Java is a perfectly acceptable (in fact quite decent) language for doing build tasks. There is nothing in ant that cannot be equally concisely written in java, given the right library support.
I have written more this subject in the articles on the website.
The website is not completely upto date, the latest version is 0.8.4.
But to replace Java by XML (as ANT/Maven does) doesn't help.
Grouping ANT/Maven together because of XML is a very superficial association to make. ANT despite what it claims is essentially an inflexible programming language, which offers very few benefits over java (and many disadvantages), except that it is interpreted (not compiled), has a library of build tasks and can be stuck in the root of a project without looking like source code. XML is a big issue in ant because it is a very poor choice for writing a programming language.
Maven is a build framework, into which you make your program fit, by decomposing it into maven projects ... etc. etc. XML is a perfectly good choice for configuration here. The core problem with Maven is poor design. For one, it has tried to make things simpler than they are, and does not recognise that some programming projects are fundamentally not amenable to a module structure (i.e. what ebuild calls products). It also makes developing across the dependency boundary (i.e. your program + the library) very cumbersome indeed.
Well there's your problem right there. Use Maven with Netbeans, and the integration between the two is so slick you'll wonder why you didn't use it to begin with. My biggest complaint in Netbeans now is that it doesn't have equally slick support for SBT and Gradle, but that's just because I've been spoiled.
> I especially find Maven unreliable in combination with eclipse.
Indeed. I have first hand experience with this. My team has a diehard Eclipse user who has added a bunch of random configuration plugins to Eclipse basically to make Eclipse work with Maven.
Compare this to IntelliJ. You can open a Maven project (even a multimodule Maven project) directly in IntelliJ. There is no project importing/conversion. It just works with the native Maven project model.
There are plenty of things to dislike about Maven but this isn't one of them.
Well there's a Junction plugin for Maven that alleges to do this. However it hasn't been updated since 2007 and relies on something no longer in a Maven repo that I could find.
But here's the point I most disagree with:
> Maven assumes there is one right way to build for everyone
A lot of people have this opinion (and prefer Ant, Gradle or something else as a result). I do not share this view. I like that Maven is opinionated about things like project structure.
Why? Because left to our own devices engineers are terrible at making these sorts of decisions. We all have a tendency to focus on some weird aesthetic and overstate its importance at the detriment of consistency across teams and projects.
I've had this argument with coworkers in relation to us having a very strict style guide for our code . Opponents call this an obstacle getting in the way of getting something done and it has a cognitive cost of internalizing what is essentially useless information and arbitrary standards.
Obviously said people haven't worked in a large engineering organization where different teams would otherwise have different line lengths, curly brace styles, indenting levels and so on. It's a good thing there's a central set of conventions for this stuff. It avoids pointless "wars" about where curly braces should go.
I feel the same way about Maven's archetypes. Fact is, you can look at any Maven WAR project and know where to find pretty much everything. You can't say the same about any Ant project.
Just like with code style, people have an exaggerated view that their particular way of doing things is right and super-important.
Being consistent is often more important than being right.
Being right is subjective more often than it isn't.
In the end the author states:
> I think Maven works fine but in the past some logical choices have been made that do no longer make sense
which kinda makes and misses the point. He's right in that it does work fine for all its warts. But changing things like XML (for YAML or SBT's DSL or whatever) is pretty much a change for change's sake at this point.
Maven is one of many tools that isn't cool but is certainly good enough. There are really bigger things to worry about. How much time do you spend editing build files anyway?
Well his opinion is perfectly true - Maven does assume there is one right way to build for everyone. You're disagreeing about whether it's a bad thing.
And here's the deal - for the 95% (or more) of projects where "The Maven Way" works, it's a good thing, for all the reasons you've stated.
But not every project fits into that, and one of Maven's limitations is that once you start to push at its boundaries, it falls apart. It doesn't provide enough flexibility to be able to stretch it into places it wasn't intended to go. And so, once your project his that point you either need to fight the tool, or throw it out and use something else. Neither is particularly desirable.
Maven is one of many tools that isn't cool but is certainly good enough.
For most cases, yes, but not always. No matter who you are, your experience is not universal enough to draw those conclusions for other people's projects.
How much time do you spend editing build files anyway?
Personally? Enough to have run into all sorts of limitations in Maven.
Not everyone is working on "Maven WAR project". There are projects with full time build engineers. Even on small projects (in terms of lines of code) if the artifacts you're producing are non-standard, then you can spend days (or even weeks) wrestling with maven to get the project under control.
Maven makes the easy things trivial, the average things easy, but it also makes the hard things nearly impossible. For the 95% that's a fine trade-off, but if you're not in that group then Maven is not going to be your friend.
I've built ETL libraries that use a completely custom lifecycle (pre-/post- extract, extract, transform & load) in Maven with a directory structure to match.
If you can't code in Java that will be hard, but it's similar to me complaining about Puppet because I can't figure out it's architecture fast enough since I don't know Ruby well enough.
P.S. Not saying you can't code in Java, but the original author did indicate the mere fact that it was Java was problematic.
Most of them being related to that Java is a compiled language so you often find yourself in a situation where you wonder about plugin internals but the actual source the plugin was built from is elsewhere. That in combination with that extensions needs to be compiled and distributed which requires infrastructure to "build the build". Sure it's easy to google and download the source, even recompile, setup a place where the plugins can be used from (custom and patched ones) but it is still extra overhead that would not be needed at all with (for instance) an interpreted language.
An interpreted language is simply a more sensible choice for these kind of things. The developers of SBT understood this and made sure the buildfile and plugins are distributed as source and compiled by SBT to make this extra step go away even if the buildfile is written in Scala.
You're framing it as an attack against just Maven though..
You realize that the 'Eclipse IDE for Java Developers' comes with official support for Maven out of the box, right? I'm not a fan of Maven, but my Eclipse-related issues have been minimal.
The deal with eclipse: I have certainly used eclipse and IntelliJ more than just once :) Eclipse's background incremental compile is unrivaled. Maven breaks this (at least broke this in 2010 when I wrote the post). It is the /one/ killer feature in eclipse and it is hard to be without once you get used to it /EVEN IF/ intelliJ and netbeans imports maven projects like charm.
Importing projects is not the issue, it's nice to have that automated and all but the issue is that the kick ass builder in eclipse was downgraded to a below average one with the eclipse plugin. I'm sad to see that people actually think that eclipse is as bad as it with the maven stuff installed :)
IMO it's better to just generate eclipsprojects from maven and stay away from the eclipseplugins at least was in 2010. Or use another IDE if one must use maven. Unlike your die hard Eclipse-user I tend to use what others in the teams are using IDE-wise which has given me experience both with IntelliJ and Eclipse and have actually come to prefer Eclipse over IntelliJ over the years... different discussion.
There were many other points other than IDE's in the post too :)
As someone else pointed out Maven actually does assume there is one right way to build and you're disagreeing that it's a bad thing.
The enterprise argument is a bit of a strawman that people tend to use when others don't agree with them. I've been in small and large organizations. "Largeness" is not an important parameter other than a belief that "things are supposed to be big hard and complicated" is more common in large enterprises.
Standards are nice, I haven't had a curly brace discussion with anyone for years now (other than to make user everybodys save actions and code formatting-settings are in sync which everyone agreed so far is a good thing). I used to have those discussions a lot years ago, I think it's a maturity thing.
You are right that declaring a POM in YAML or a DSL is pretty much a change for changes sake (as I have understood is the case in Maven 3). The real benefit would be if one would actually do something different with the language than declare a POM.
Thank you so much for the attention!
The simple task of 'given a jar artifact(1), and its md5, full source code and pom, reproduce it from scratch' never works. (One of the reasons being the jar tool that stores .class file dates inside the jar).
Another reason is that maven self-updates, and sometimes this gets in the way of being able to build an older project. I'm pretty sure there are several jars in biblio that cannot be recreated (never mind the md5) without significant hacking.
(1) there is a difference between 'artefact' and 'artifact', but somehow the semantics became confused.
I suspect most people who criticise maven haven't worked in corporate environments where there are just a lot of projects, a lot of people, and a lot of churn (both in people and projects). That's where maven is a life saver.
Corporate environments want droneish, politically correct, interchangeable programmers who very rarely step outside of their predefined, straitjacketed roles.
I think most people that criticize Maven do so because Maven does not help them do their job to the extent Maven should.
Enterprises don't really need enterprise tools but you need an enterprise to use enterprise tools...
I am not that well versed in build systmes, but I have never seen another build system that does this. Usually version numbers is stored in some meta data not in filenames.
Gradle? It's better than Maven, but they picked the wrong scripting language. Builds should be interpreted, not compiled. It's painful to leverage code that you need to build as you are in a catch 22 situation - can't reference a class in a gradle file that hasn't been built yet.